做seo为什么要了解网站,俐侎族网站建设背景,阿里云如何查看已建设好的网站,河南网站建设最简单的基于 FFmpeg 的收流器#xff08;以接收 RTMP 为例#xff09; 最简单的基于 FFmpeg 的收流器#xff08;以接收 RTMP 为例#xff09;正文结果工程文件下载参考链接 最简单的基于 FFmpeg 的收流器#xff08;以接收 RTMP 为例#xff09;
参考雷霄骅博士的文章… 最简单的基于 FFmpeg 的收流器以接收 RTMP 为例 最简单的基于 FFmpeg 的收流器以接收 RTMP 为例正文结果工程文件下载参考链接 最简单的基于 FFmpeg 的收流器以接收 RTMP 为例
参考雷霄骅博士的文章链接最简单的基于FFMPEG的推流器附件收流器
正文
出于对 最简单的基于 FFmpeg 的推流器以推送 RTMP 为例的补充本文记录一个最简单的基于 FFmpeg 的收流器。
收流器和推流器的作用正好相反推流器用于将本地文件以流媒体的形式发送出去而收流器用于将流媒体内容保存为本地文件。
本文记录的推流器可以将 RTMP 流媒体保存成为一个本地的 FLV 文件。由于 FFmpeg 本身支持很多的流媒体协议和封装格式所以也支持其它的封装格式和流媒体协议。
源程序
// Simplest FFmpeg Receiver.cpp : 定义控制台应用程序的入口点。
///**
* 最简单的基于 FFmpeg 的收流器接收 RTMP
* Simplest FFmpeg Receiver (Receive RTMP)
*
* 源程序
* 雷霄骅 Lei Xiaohua
* leixiaohua1020126.com
* 中国传媒大学/数字电视技术
* Communication University of China / Digital TV Technology
* http://blog.csdn.net/leixiaohua1020
*
* 修改
* 刘文晨 Liu Wenchen
* 812288728qq.com
* 电子科技大学/电子信息
* University of Electronic Science and Technology of China / Electronic and Information Science
* https://blog.csdn.net/ProgramNovice
*
* 本例子将流媒体数据以 RTMP 为例保存成本地文件。
* 是使用 FFmpeg 进行流媒体接收最简单的教程。
*
* This example saves streaming media data (Use RTMP as example)
* as a local file.
* Its the simplest FFmpeg stream receiver.
*/#include stdafx.h#include stdio.h
#include stdlib.h// 解决报错fopen: This function or variable may be unsafe.Consider using fopen_s instead.
#pragma warning(disable:4996)// 解决报错无法解析的外部符号 __imp__fprintf该符号在函数 _ShowError 中被引用
#pragma comment(lib, legacy_stdio_definitions.lib)
extern C
{// 解决报错无法解析的外部符号 __imp____iob_func该符号在函数 _ShowError 中被引用FILE __iob_func[3] { *stdin, *stdout, *stderr };
}#define __STDC_CONSTANT_MACROS#ifdef _WIN32
// Windows
extern C
{
#include libavformat/avformat.h
#include libavutil/mathematics.h
#include libavutil/time.h
};
#else
// Linux...
#ifdef __cplusplus
extern C
{
#endif
#include libavformat/avformat.h
#include libavutil/mathematics.h
#include libavutil/time.h
#ifdef __cplusplus
};
#endif
#endif// 1: Use H.264 Bitstream Filter
#define USE_H264BSF 0int main(int argc, char* argv[])
{AVOutputFormat *ofmt NULL;// Input AVFormatContext and Output AVFormatContextAVFormatContext *ifmt_ctx NULL, *ofmt_ctx NULL;AVPacket pkt;const char *in_filename, *out_filename;int ret, i;int videoindex -1;int frame_index 0;// RTMPin_filename rtmp://liteavapp.qcloud.com/live/liteavdemoplayerstreamid;// UDP// in_filename rtp://233.233.233.233:6666;out_filename receive.flv;// out_filename receive.ts;// out_filename receive.mkv;av_register_all();// Init networkavformat_network_init();// Inputif ((ret avformat_open_input(ifmt_ctx, in_filename, 0, 0)) 0){printf(Could not open input file.);goto end;}if ((ret avformat_find_stream_info(ifmt_ctx, 0)) 0){printf(Failed to retrieve input stream information);goto end;}for (i 0; i ifmt_ctx-nb_streams; i)if (ifmt_ctx-streams[i]-codec-codec_type AVMEDIA_TYPE_VIDEO){videoindex i;break;}// Print some input informationav_dump_format(ifmt_ctx, 0, in_filename, 0);// Outputavformat_alloc_output_context2(ofmt_ctx, NULL, NULL, out_filename); // RTMPif (ofmt_ctx NULL){printf(Could not create output context.\n);ret AVERROR_UNKNOWN;goto end;}ofmt ofmt_ctx-oformat;for (i 0; i ifmt_ctx-nb_streams; i){// Create output AVStream according to input AVStreamAVStream *in_stream ifmt_ctx-streams[i];AVStream *out_stream avformat_new_stream(ofmt_ctx, in_stream-codec-codec);if (out_stream NULL){printf(Failed allocating output stream.\n);ret AVERROR_UNKNOWN;goto end;}// Copy the settings of AVCodecContextret avcodec_copy_context(out_stream-codec, in_stream-codec);if (ret 0){printf(Failed to copy context from input to output stream codec context.\n);goto end;}out_stream-codec-codec_tag 0;if (ofmt_ctx-oformat-flags AVFMT_GLOBALHEADER){out_stream-codec-flags | CODEC_FLAG_GLOBAL_HEADER;}}// Print some output informationav_dump_format(ofmt_ctx, 0, out_filename, 1);// Open output URLif (!(ofmt-flags AVFMT_NOFILE)){ret avio_open(ofmt_ctx-pb, out_filename, AVIO_FLAG_WRITE);if (ret 0){printf(Could not open output URL %s.\n, out_filename);goto end;}}// Write file headerret avformat_write_header(ofmt_ctx, NULL);if (ret 0){printf(Error occurred when opening output URL.\n);goto end;}#if USE_H264BSFAVBitStreamFilterContext* h264bsfc av_bitstream_filter_init(h264_mp4toannexb);
#endifwhile (1){AVStream *in_stream, *out_stream;// Get an AVPacketret av_read_frame(ifmt_ctx, pkt);if (ret 0){break;}in_stream ifmt_ctx-streams[pkt.stream_index];out_stream ofmt_ctx-streams[pkt.stream_index];// copy packet// Convert PTS/DTSpkt.pts av_rescale_q_rnd(pkt.pts, in_stream-time_base, out_stream-time_base,(AVRounding)(AV_ROUND_NEAR_INF | AV_ROUND_PASS_MINMAX));pkt.dts av_rescale_q_rnd(pkt.dts, in_stream-time_base, out_stream-time_base,(AVRounding)(AV_ROUND_NEAR_INF | AV_ROUND_PASS_MINMAX));pkt.duration av_rescale_q(pkt.duration, in_stream-time_base, out_stream-time_base);pkt.pos -1;if (pkt.stream_index videoindex){printf(Receive %8d video frames from input URL.\n, frame_index);frame_index;#if USE_H264BSFav_bitstream_filter_filter(h264bsfc, in_stream-codec, NULL, pkt.data, pkt.size, pkt.data, pkt.size, 0);
#endif}// ret av_write_frame(ofmt_ctx, pkt);ret av_interleaved_write_frame(ofmt_ctx, pkt);if (ret 0){printf(Error muxing packet.\n);break;}av_free_packet(pkt);
}#if USE_H264BSFav_bitstream_filter_close(h264bsfc);
#endif// Write file trailerav_write_trailer(ofmt_ctx);
end:avformat_close_input(ifmt_ctx);// Close outputif (ofmt_ctx !(ofmt-flags AVFMT_NOFILE)){avio_close(ofmt_ctx-pb);}avformat_free_context(ofmt_ctx);if (ret 0 ret ! AVERROR_EOF){printf(Error occurred.\n);return -1;}system(pause);return 0;
}结果
运行程序输出如下 程序运行之后即可获取流媒体数据并且在本地保存成一个视频文件 “receive.flv”。 工程文件下载
GitHubUestcXiye / Simplest-FFmpeg-Receiver
CSDNSimplest FFmpeg Receiver.zip
参考链接
最简单的基于 FFmpeg 的推流器以推送 RTMP 为例