ffmpeg
| Kind | ffi-c |
|---|---|
| Capabilities | ffi file process |
| Categories | multimedia video audio |
| Keywords | ffmpeg video audio media encoding decoding transcoding |
FFmpeg bindings for Kit - video and audio processing
Files
| File | Description |
|---|---|
.editorconfig | Editor formatting configuration |
.gitignore | Git ignore rules for build artifacts and dependencies |
.tool-versions | asdf tool versions (Zig, Kit) |
LICENSE | MIT license file |
README.md | This file |
c/kit_ffmpeg.c | C FFI wrapper implementation |
c/kit_ffmpeg.h | C header for FFI wrapper |
examples/convert.kit | Video conversion example |
examples/frames.kit | Frame extraction example |
examples/info.kit | Media information example |
examples/thumbnail.kit | Thumbnail generation example |
kit.toml | Package manifest with metadata, native build settings, and dependencies |
src/ffmpeg.kit | Kit FFmpeg bindings and high-level media API |
tests/ffmpeg.test.kit | Tests for ffmpeg |
Dependencies
No Kit package dependencies.
This package requires FFmpeg development libraries:
| Platform | Install |
|---|---|
| macOS | brew install ffmpeg |
| Ubuntu/Debian | sudo apt install libavcodec-dev libavformat-dev libavutil-dev libswscale-dev libswresample-dev |
| Fedora | sudo dnf install ffmpeg-devel |
Installation
kit add gitlab.com/kit-lang/packages/kit-ffmpeg.gitUsage
import Kit.Ffmpeg as Ffmpeg
main = fn =>
# Open a media file and read its metadata
match Ffmpeg.open "sample.mp4"
| Err e ->
println "Failed to open sample.mp4: ${e}"
| Ok media ->
# Ensure FFmpeg resources are released when this scope exits
defer Ffmpeg.close media
println "Format: ${Ffmpeg.format media}"
println "Duration: ${Ffmpeg.duration-string-long media}"
println "Resolution: ${Ffmpeg.resolution-string media}"
println "Bitrate: ${Ffmpeg.bitrate-string media}"
if Ffmpeg.has-video? media then
println "Video codec: ${Ffmpeg.video-codec media}"
println "FPS: ${Float.to-string (Ffmpeg.fps media)}"
else
no-op
if Ffmpeg.has-audio? media then
println "Audio codec: ${Ffmpeg.audio-codec media}"
println "Sample rate: ${Int.to-string (Ffmpeg.sample-rate media)} Hz"
else
no-op
# Extract one RGB frame at two seconds
match Ffmpeg.extract-frame media 2.0
| Ok frame ->
defer Ffmpeg.free-frame frame
width = Ffmpeg.frame-width frame
height = Ffmpeg.frame-height frame
center = Ffmpeg.get-pixel frame (width / 2) (height / 2)
println "Frame: ${Int.to-string width}x${Int.to-string height}"
println "Center pixel: R=${Int.to-string center.r} G=${Int.to-string center.g} B=${Int.to-string center.b}"
| Err e ->
println "Frame extraction failed: ${e}"
# Save a PPM thumbnail
match Ffmpeg.generate-thumbnail media 320 180 "thumb.ppm"
| Ok _ -> println "Saved thumb.ppm"
| Err e -> println "Thumbnail failed: ${e}"
mainDevelopment
Running Examples
Run examples with the interpreter:
kit run examples/info.kitCompile examples to a native binary:
kit build examples/info.kit && ./infoNote: The examples expect media files such as sample.mp4 or input.avi in the current directory.
Running Tests
Run the test suite:
kit testRun the test suite with coverage:
kit test --coverageRunning kit dev
Run the standard development workflow (format, check, and test):
kit devThis will:
- Build the native FFmpeg wrapper when needed
- Format and check source files in
src/ - Type check examples in
examples/ - Run tests in
tests/with coverage
Running Parity
Run interpreter/compiler parity checks for the examples:
kit parity --failures-onlyGenerating Documentation
Generate API documentation from doc comments:
kit docNote: Kit sources with doc comments (##) will generate HTML documents in docs/*.html.
Cleaning Build Artifacts
Remove generated files, caches, and build artifacts:
kit task cleanNote: Defined in kit.toml.
Local Installation
To install this package locally for development:
kit installThis installs the package to ~/.kit/packages/@kit/ffmpeg/, builds the native libkit_ffmpeg wrapper, and makes it available for import as Kit.Ffmpeg in other projects.
License
This package is released under the MIT License - see LICENSE for details.
FFmpeg is distributed under its own license terms. Check the license of the FFmpeg build you link against.
Exported Functions & Types
FFMPEGError
FFMPEG error type with specific variants for different failure modes.
Variants
FFMPEGOpenError {message}FFMPEGExtractError {message}FFMPEGProcessError {message}open
============================================================ Media File Information ============================================================
Open a media file and read its metadata.
This is typically the first function called when working with a media file. It opens the file and reads header information to extract metadata about video and audio streams.
Parameters:
path- String - Path to the media file to open
Returns: Result - Ok with media handle on success, or Err with error message
NonEmptyString -> Result {ptr: Ptr, path: String} FFMPEGError
result = open "movie.mp4"
match result
| Ok media -> print-info media
| Err msg -> print "Error: ${message}"
close
Close a media file and free associated resources.
Should be called when done working with a media file to release FFmpeg resources.
Parameters:
media- Record - Media handle returned from open
Returns: () - Unit value
{ptr: Ptr, ..} -> ()
format
Get the container format name.
Returns the name of the container format (e.g., "mp4", "matroska", "avi", "mov").
Parameters:
media- Record - Media handle returned from open
Returns: String - Format name
{ptr: Ptr, ..} -> String
duration
Get the total duration of the media file in seconds.
Parameters:
media- Record - Media handle returned from open
Returns: Float - Duration in seconds
{ptr: Ptr, ..} -> Float
bitrate
Get the overall bitrate in bits per second.
This is the combined bitrate of all streams (video + audio).
Parameters:
media- Record - Media handle returned from open
Returns: Int - Bitrate in bits per second
{ptr: Ptr, ..} -> Int
width
Get the width of the video stream in pixels.
Parameters:
media- Record - Media handle returned from open
Returns: Int - Width in pixels, or 0 if no video stream
{ptr: Ptr, ..} -> Int
height
Get the height of the video stream in pixels.
Parameters:
media- Record - Media handle returned from open
Returns: Int - Height in pixels, or 0 if no video stream
{ptr: Ptr, ..} -> Int
fps
Get the frame rate (frames per second) of the video stream.
Parameters:
media- Record - Media handle returned from open
Returns: Float - Frame rate in frames per second
{ptr: Ptr, ..} -> Float
video-codec
Get the name of the video codec.
Returns codec names like "h264", "vp9", "hevc", "av1", etc.
Parameters:
media- Record - Media handle returned from open
Returns: String - Video codec name
{ptr: Ptr, ..} -> String
audio-codec
Get the name of the audio codec.
Returns codec names like "aac", "mp3", "opus", "vorbis", etc.
Parameters:
media- Record - Media handle returned from open
Returns: String - Audio codec name
{ptr: Ptr, ..} -> String
sample-rate
Get the audio sample rate in Hz.
Common sample rates are 44100 Hz, 48000 Hz, 96000 Hz.
Parameters:
media- Record - Media handle returned from open
Returns: Int - Sample rate in Hz
{ptr: Ptr, ..} -> Int
channels
Get the number of audio channels.
Common values are 1 (mono), 2 (stereo), 6 (5.1 surround).
Parameters:
media- Record - Media handle returned from open
Returns: Int - Number of audio channels
{ptr: Ptr, ..} -> Int
has-video?
Check if the file contains a video stream.
Parameters:
media- Record - Media handle returned from open
Returns: Bool - True if file has a video stream, false otherwise
{ptr: Ptr, ..} -> Bool
has-audio?
Check if the file contains an audio stream.
Parameters:
media- Record - Media handle returned from open
Returns: Bool - True if file has an audio stream, false otherwise
{ptr: Ptr, ..} -> Bool
info
Get all media information as a record.
Convenience function that gathers all metadata into a single record.
Parameters:
media- Record - Media handle returned from open
Returns: Record - Record containing all media metadata with fields:format, duration, bitrate, width, height, fps,video-codec, audio-codec, sample-rate, channels,has-video, has-audio
{ptr: Ptr, ..} -> {format: String, duration: Float, bitrate: Int, width: Int, height: Int, fps: Float, video-codec: String, audio-codec: String, sample-rate: Int, channels: Int, has-video: Bool, has-audio: Bool}
result = open "video.mp4"
match result
| Ok media ->
info-rec = info media
print "Resolution: ${Int.to-string info-rec.width}x${Int.to-string info-rec.height}"
| Err msg -> print msg
print-info
Print formatted media information to stdout.
Displays format, duration, bitrate, video specs (if present), and audio specs (if present).
Parameters:
media- Record - Media handle returned from open
Returns: () - Unit value
{ptr: Ptr, ..} -> ()
result = open "video.mp4"
match result
| Ok media ->
print-info media
close media
| Err msg -> print msg
extract-frame
{ptr: Ptr, ..} -> Float -> Result {ptr: Ptr, width: Int, height: Int} FFMPEGError
free-frame
{ptr: Ptr, ..} -> ()
frame-width
{width: Int, ..} -> Int
frame-height
{height: Int, ..} -> Int
pixel-r
{ptr: Ptr, ..} -> Int -> Int -> Int
pixel-g
{ptr: Ptr, ..} -> Int -> Int -> Int
pixel-b
{ptr: Ptr, ..} -> Int -> Int -> Int
get-pixel
{ptr: Ptr, ..} -> Int -> Int -> {r: Int, g: Int, b: Int}
save-thumbnail
{ptr: Ptr, ..} -> Float -> PositiveInt -> PositiveInt -> NonEmptyString -> Result () FFMPEGError
generate-thumbnail
{ptr: Ptr, ..} -> PositiveInt -> PositiveInt -> NonEmptyString -> Result () FFMPEGError
extract-audio
{ptr: Ptr, ..} -> Float -> Float -> Result {ptr: Ptr, num-samples: Int} FFMPEGError
free-audio
{ptr: Ptr, ..} -> ()
audio-num-samples
{num-samples: Int, ..} -> Int
audio-get-sample
{ptr: Ptr, ..} -> NonNegativeInt -> Float
create-transcoder
NonEmptyString -> NonEmptyString -> Int -> Int -> Int -> Result {ptr: Ptr} FFMPEGError
transcode-process
{ptr: Ptr, ..} -> Int
transcode-finish
{ptr: Ptr, ..} -> ()
convert
NonEmptyString -> NonEmptyString -> Int -> Int -> Int -> Result () FFMPEGError
convert-simple
NonEmptyString -> NonEmptyString -> Result () FFMPEGError
convert-resize
NonEmptyString -> NonEmptyString -> PositiveInt -> PositiveInt -> Result () FFMPEGError
guess-format
NonEmptyString -> String
can-encode?
String -> Bool
can-decode?
String -> Bool
resolution-string
{ptr: Ptr, ..} -> String
duration-string
{ptr: Ptr, ..} -> String
duration-string-long
{ptr: Ptr, ..} -> String
bitrate-string
{ptr: Ptr, ..} -> String
is-video?
{ptr: Ptr, ..} -> Bool
is-audio-only?
{ptr: Ptr, ..} -> Bool