| FFmpeg offers several libraries, primarily the libavcodec, libavformat, libavfilter, and libswscale libraries, that can be directly integrated into C/C++ applications without using the command-line interface. These libraries provide functions for encoding and decoding various audio and video formats, manipulating streams, and applying filters, allowing developers to incorporate powerful multimedia processing capabilities into their software. Bindings exist for other languages like Python, enabling their use in a wider range of applications. Below are examples of using FFmpeg libraries to encode a video file in MP4 format in C++, Rust, and Python.
C++ ExampleUsing the native FFmpeg libraries: extern "C" {
#include <libavformat/avformat.h>
#include <libavcodec/avcodec.h>
#include <libswscale/swscale.h>
#include <libavutil/opt.h>
}
int main() {
const char *output_file = "output.mp4";
// Initialize FFmpeg library
avformat_network_init();
AVFormatContext *fmt_ctx = nullptr;
AVCodecContext *codec_ctx = nullptr;
AVStream *video_stream = nullptr;
AVCodec *codec = nullptr;
// Create output format context
avformat_alloc_output_context2(&fmt_ctx, nullptr, "mp4", output_file);
if (!fmt_ctx) {
fprintf(stderr, "Could not allocate output format context\n");
return -1;
}
// Find H.264 codec
codec = avcodec_find_encoder(AV_CODEC_ID_H264);
if (!codec) {
fprintf(stderr, "Codec not found\n");
return -1;
}
// Create video stream
video_stream = avformat_new_stream(fmt_ctx, codec);
if (!video_stream) {
fprintf(stderr, "Could not allocate stream\n");
return -1;
}
// Configure codec context
codec_ctx = avcodec_alloc_context3(codec);
codec_ctx->codec_id = codec->id;
codec_ctx->codec_type = AVMEDIA_TYPE_VIDEO;
codec_ctx->width = 1280;
codec_ctx->height = 720;
codec_ctx->time_base = {1, 25}; // 25 FPS
codec_ctx->framerate = {25, 1};
codec_ctx->pix_fmt = AV_PIX_FMT_YUV420P;
avcodec_open2(codec_ctx, codec, nullptr);
avcodec_parameters_from_context(video_stream->codecpar, codec_ctx);
// Open output file
if (!(fmt_ctx->oformat->flags & AVFMT_NOFILE)) {
avio_open(&fmt_ctx->pb, output_file, AVIO_FLAG_WRITE);
}
// Write file header
avformat_write_header(fmt_ctx, nullptr);
// Encoding loop omitted for brevity (would encode frames here)
// Write file trailer
av_write_trailer(fmt_ctx);
// Free resources
avcodec_free_context(&codec_ctx);
avformat_free_context(fmt_ctx);
return 0;
}
Rust ExampleUsing the ffmpeg-rs library: use ffmpeg_next as ffmpeg;
fn main() -> Result<(), ffmpeg::Error> {
ffmpeg::init()?;
let output_file = "output.mp4";
let mut output = ffmpeg::format::output(&output_file)?;
let codec = ffmpeg::codec::encoder::find(ffmpeg::codec::Id::H264)
.ok_or(ffmpeg::Error::EncoderNotFound)?;
let mut stream = output.add_stream(codec)?;
{
let mut encoder = stream.codec().encoder().video()?;
encoder.set_width(1280);
encoder.set_height(720);
encoder.set_format(ffmpeg::format::Pixel::YUV420P);
encoder.set_time_base((1, 25)); // 25 FPS
encoder.open_as(codec)?;
}
output.write_header()?;
// Encoding loop omitted for brevity
output.write_trailer()?;
Ok(())
}
Python ExampleUsing PyAV for Python bindings: import av
# Create an output container
output_file = "output.mp4"
container = av.open(output_file, mode='w')
# Add a video stream with H.264 codec
stream = container.add_stream("h264", rate=25)
stream.width = 1280
stream.height = 720
stream.pix_fmt = "yuv420p"
# Encoding loop (normally you would write frames here)
for frame_idx in range(100): # Example: 100 blank frames
frame = av.VideoFrame(1280, 720, 'yuv420p')
packet = stream.encode(frame)
if packet:
container.mux(packet)
# Finalize the file
container.close()
Notes:- C++: Requires linking against FFmpeg libraries during compilation (e.g.,
-lavcodec -lavformat -lavutil -lswscale). - Rust: The
ffmpeg-rs library provides safe bindings but requires FFmpeg to be installed on the system. - Python: PyAV is a high-level library that makes it easier to work with FFmpeg functionality compared to direct bindings. Install with
pip install av.
Let me know if you'd like further clarification or additional examples! |