You write widgets. Fluvie shoots the film.
Fluvie is a Flutter package that turns widget code into real video files. You
build a video the way you build a screen, with Scenes and the Flutter widgets
you already know, you say how long each thing lasts, and Fluvie renders every
frame and encodes it into an MP4 (or a GIF, or an image sequence) with FFmpeg. No
video editor, no manual timeline, no After Effects.
Think of it as a tiny film studio that already speaks Flutter: you direct, Fluvie handles continuity, and FFmpeg runs the projector. No timeline to scrub, no keyframe spreadsheet, no 2am debugging because frame 412 is one pixel off.
- Declarative. Compose
Scenes and elements like any Flutter screen. - Cacheable. The frame cache keys on content, so caching, golden tests, and batch rendering just work.
- Headless. Render from the CLI, an HTTP API, or an MCP server. No display needed.
- Conversational. Describe a video in plain language; a model writes editable Fluvie code (or a spec) and renders it.
This is lesson 01, in full: about 16 lines of widgets become a 4 second clip.
dart pub global activate fluvie_cli
fluvie init --dir my_reel # a composition, an assets/ folder, a pubspec
cd my_reel && flutter pub get
fluvie preview ./lib/example_video.dart # live, hot-reloading
fluvie render ./lib/example_video.dart --out reel.mp4 # the fileA Fluvie project is a composition file, an assets/ folder, and a pubspec. There
is no app, no harness, and no registry: preview and render take the .dart
file and generate whatever they need. The file exposes a top-level Video build().
You do not need to install FFmpeg: the first render
downloads a pinned, checksum-verified build and caches it (run
fluvie ffmpeg install to fetch it ahead of time, or point --ffmpeg /
FLUVIE_FFMPEG at your own). The
getting started guide
walks through it. Full source:
examples/gallery/lib/lessons/01_hello_video.dart.
These snippets are trimmed to the shape of the thing; each links to its full, runnable lesson. The clips beside them were rendered by Fluvie.
Full source: examples/gallery/lib/lessons/07_charts.dart.
Several scenes play one after another with a cross-fade. Each scene stacks layers: a full-frame effect under the content, a chip that pops on the music beat, captions over the top.
Full source: examples/gallery/lib/lessons/12_the_kitchen_sink.dart.
Thirteen runnable lessons live in examples/gallery/lib/lessons/,
from "Hello, Fluvie" to the kitchen sink. Try them at
demo.fluvie.dev: write and render a Video in the
Playground, or describe one in the AI Assistant and let a model write and
render the code. Or run the gallery locally:
flutter run --enable-impeller # from the repo root; Impeller for the live previewBeyond the gallery, examples/ has a small kitten-themed app for
each rendering path: a CLI quickstart, a Linux desktop studio, an Android
on-device app, an in-browser maker, and a server-render studio. See
Example apps.
Use Impeller (
--enable-impeller) whenever you run or preview Fluvie on the desktop. It is Flutter's current renderer and draws shaders, grain, and blends the way the final video does. The headless render pipeline already handles this for you. See Troubleshooting.
Most people only need fluvie. The rest are there when you want to render in
CI, on a server, or from an AI assistant.
| Package | Role | pub.dev |
|---|---|---|
fluvie |
The library. Describe a video, render an MP4. | |
fluvie_cli |
Headless renderer. Capture with flutter test, encode with FFmpeg. |
|
fluvie_lints |
Lint rules that catch timing and layering mistakes. | |
fluvie_validate |
Check a Video snippet before you render it: the analyzer plus the lint rules, in-process, never executed. |
|
fluvie_ai |
Author a video from a prompt. A model writes a spec. Built on ai_abstracted. |
|
fluvie_server |
One self-hostable server: render API (local or S3), MCP server, and a docs helper, plus a web-safe client. | |
fluvie_mobile_encoder |
Render to MP4 fully on-device on Android and iOS, no FFmpeg. | |
fluvie_web_encoder |
Render to MP4 fully in the browser with ffmpeg.wasm, opt-in. |
The same Video renders three ways. Pick by where the encode should run: on your
own machine, on a server you call, or on the user's own device.
| Platform | Local (FFmpeg binary) | Server API | On-device |
|---|---|---|---|
| Desktop (Linux/macOS/Windows) | ✅ fluvie_cli |
✅ fluvie_server client |
✅ local FFmpeg (the CLI itself) |
| Android | — | ✅ fluvie_server client |
✅ fluvie_mobile_encoder (native) |
| iOS | — | ✅ fluvie_server client |
✅ fluvie_mobile_encoder (native) |
| Web (browser) | — | ✅ fluvie_server client |
✅ fluvie_web_encoder (ffmpeg.wasm, opt-in) |
- Local runs FFmpeg on your own machine. It is the full feature set (audio, GIF, transparency) and the reference platform for golden images. This is the CLI and CI path.
- Server API keeps the client thin: the app sends a spec, a render server runs FFmpeg, the app gets a file back. It works on every platform and keeps app bundles small. Use it when you do not want to ship an encoder.
- On-device renders without a server, so the video never leaves the device. Mobile uses the platform's native encoder; web uses ffmpeg.wasm. The frames are captured by Fluvie's own pipeline, so they match a desktop render; only the encode edge differs (see each guide for the trade-offs).
Combining platforms. One Flutter app can run on mobile and web and render
on-device on both: choose the renderer per platform behind a conditional import
(fluvie_mobile_encoder on mobile, fluvie_web_encoder on web), passing the same
Video. On the web you trade bundle size for the ffmpeg.wasm payload; choose the
Server API instead to keep the bundle light.
Audio works everywhere too. Declare Audio.music/Audio.sfx once and it
mixes on every renderer — looping beds, fades, trims, and multi-track amix —
with audio opt-in on-device. The web has no local-file source (bundle as an asset
or fetch from an allowlisted URL). See the full
audio support by platform
table.
The library is the whole show. These hosted pieces are the lobby, the trailers, and the box office.
| Where | What you get |
|---|---|
| fluvie.dev | The front of house: what Fluvie is, in one screen. |
| docs.fluvie.dev | The manual: getting started, guides, a cookbook, and the full reference. |
| demo.fluvie.dev | The screening room: try Fluvie live in the browser and render a clip. |
| mcp.fluvie.dev | The hosted MCP server, so an AI assistant can make videos with Fluvie. |
Start at docs.fluvie.dev:
- Getting started: install, your first video, the core ideas.
- Guides: animation, audio, charts, code scenes, theming, exporting.
- Cookbook: short, copy-paste recipes for one task each.
- AI and MCP: author from a prompt, run it locally, or point Claude at it.
- Reference: the whole public surface on one page.
Everything you can paint with Flutter, plus the things a video needs:
| Kind | What you get |
|---|---|
| Text | Text, Typewriter, Counter, Markdown |
| Code | Code, CodeReveal (animated diffs), Terminal |
| Media | Image, Clip (embedded video), Snapshot, DeviceFrame |
| Data | Chart (bar, line, area, pie, donut, scatter), Bars |
| Diagrams and web | Mermaid, WebView, Html |
| Annotations | Shape, Arrow, Connector, Callout, Spotlight, LowerThird, TitleCard |
| Motion and effects | 60+ animation presets, Stagger, Camera, shaders, particles, grain |
| Audio | Audio (music and sfx), beat detection, Captions (SRT and VTT) |
| Look | Background (color, gradient, image), FluvieTheme, multi-aspect export |
| Use case | For example |
|---|---|
| Product demos | feature walkthroughs, onboarding clips, changelog videos |
| Social reels | 9:16 vertical shorts for TikTok, Reels, and Shorts |
| Explainers | tutorials and concept animations |
| Data stories | stat highlight reels and animated reports |
| Developer content | code walkthroughs, terminal demos, release notes |
| Branding | title cards, intros, and lower thirds |
Text renders as solid white boxes. That is Flutter's Ahem test font, which
draws every glyph as a filled box, so each word looks like a bar. It means the
real fonts were not loaded before the frames were captured. Fluvie's own render
pipeline (the CLI, the API, and the Docker image) loads them for you, including
the harness it generates for each render. If you host renderVideo yourself,
load the app fonts and pass defaultFontFamily before rendering.
Shaders, grain, or blends look off in the rendered file. Capture with Impeller, Flutter's current renderer:
fluvie render ./lib/my_video.dart --out out.mp4 --enable-impellerThe flag passes --enable-impeller to flutter test, so the capture rasterizes
with Impeller instead of the default tester backend. An ordinary render does not
need it; reach for it when a shader or a blend mode looks wrong.
Pull up a chair. Read CONTRIBUTING.md, install the hooks once, and keep the gate green:
dart pub get && dart run melos bootstrap
bash .githooks/install.sh
CI=true dart run melos run gate- Discussions: questions and ideas.
- Issues: bugs and feature requests.
- Code of Conduct and Security policy.
MIT © 2026 Simon Auer.


