Skip to content
streamneo.
Setup Guides12 min read

How to Burn Subtitles into Videos for an FFmpeg YouTube Playlist Stream

Learn how FFmpeg burns subtitles into video, check libass support, render a test, and plan the separate steps for a YouTube playlist stream.

sn.
StreamNeoPublished 4 October 2026
Worth sharing?

FFmpeg can burn subtitles into a video by rendering them onto each frame with its subtitles filter. You need a build that includes libass, and once rendered, the words are part of the picture: viewers cannot switch them off or choose them as a separate caption track.

The filter command below illustrates an offline render, not a complete playlist or YouTube Live setup. A real stream also needs a playlist workflow, an encoder configuration and a destination from YouTube; those depend on how your clips and channel are arranged.

Burned-in text or selectable captions

Burned-in, or hardcoded, subtitles are visible wherever the resulting video is played. FFmpeg decodes video frames, draws the subtitle text on them, and encodes the changed frames into a new video stream. A player sees one image with text in it, rather than an image accompanied by a caption track.

That distinction is useful when the words must always appear in a particular position and style, such as a translated bhajan lyric or a location label on a local news loop. It is a poor fit if viewers should be able to hide captions, change languages, or adjust their appearance. Hardcoded text cannot offer those controls.

A separate caption track follows a different workflow. YouTube’s caption tools allow captions to be provided independently of the picture, so viewers can use the controls available to them. If accessibility or multiple languages matter, retain a suitable caption workflow rather than treating burned-in text as its replacement. You can also publish a video with both visible text and a separate caption track, provided you prepare each deliberately.

Workflow What viewers receive Main trade-off
Burn subtitles with FFmpeg Text permanently composed into the video image Consistent appearance, but no viewer toggle or language choice from that text
Provide a separate caption track Video plus selectable caption data Viewer control, but captions must be supplied and managed as a track

Before you prepare a full archive, decide which experience you intend. If your goal is to play successive pre-recorded clips through a live encoder, the separate OBS playlist streaming workflow is useful context, though the rendering steps here apply to FFmpeg. If you are making a YouTube playlist of published videos, that is a different thing from feeding clips successively into one live broadcast.

Check that your FFmpeg build has libass

The subtitles filter is not present in every FFmpeg build. The FFmpeg documentation states that the filter requires a build configured with --enable-libass; installing FFmpeg alone does not establish that the feature is available. Check the official filter documentation and your local build before preparing files or writing a longer script.

Start by asking FFmpeg to list filters and look for subtitles:

ffmpeg -filters

The output should include a video filter named subtitles. If it is absent, the filter cannot be used with that executable. You may have another FFmpeg installation on the system, so check which executable your shell is calling as well as the version and build configuration. On a system with multiple packages, a terminal, desktop application or scheduled job can resolve a different executable from the one you tested.

You can also inspect the build configuration:

ffmpeg -buildconf

Look for --enable-libass. The configuration flag and the filter listing are complementary clues; if the filter is missing, resolve that before moving on. Choose a build that includes the dependency for your operating system and deployment, and verify the actual binary used in the workflow. Do not assume a downloaded or preinstalled binary has the same options as another one.

If FFmpeg reports No such filter: subtitles, this points first to build capability, not a mistake in your SRT contents. If the filter exists but complains about a file or style expression later, then investigate paths, quoting and subtitle syntax. Keep these failure types separate; changing subtitle text cannot add libass support to a build that lacks it.

Prepare and verify the subtitle file

Subtitles may be an external text file, such as SRT or ASS, or a text subtitle stream inside a media container. First establish what you have. An external file should correspond to the clip’s language and timing; a media file may contain several subtitle streams, including different languages or formats. The filter supports subtitle files and selecting subtitle streams, but you must identify the intended source rather than guess.

Use clear filenames that pair each clip with its subtitle file, for example morning-prayer.mp4 and morning-prayer.en.srt. Check the file opens as text and contains cues with start and end times and readable text. Watch for character encoding problems, unexpected blank cues, or a subtitle file that actually belongs to a different edit of the video. Even a small edit at the beginning can shift every later cue.

If the subtitle is embedded in the video, inspect the available streams with FFmpeg or a media inspection tool and note the subtitle stream index and language metadata. A file may have an English track and another language, or a non-text subtitle format that does not behave like SRT. Do not assume the first subtitle stream is the one you want. Use the appropriate input and stream selection in the filter expression, following the FFmpeg filter documentation for the syntax of your version.

Paths deserve care. The simple example uses a relative filename, which works only when the command runs in a directory where that file can be found. For spaces or punctuation in paths, quoting and escaping rules differ between the shell, operating system and FFmpeg filtergraph. Keep the filter expression quoted, but do not treat one escaping recipe as universal. Test with the actual path and shell that will run the job.

For a playlist with one subtitle file per clip, maintain a clear mapping between video and subtitles. Do not place all files in a folder and rely on sorting order alone; names, durations and language labels should make pairing evident. The playlist guide for a continuous devotional stream can help frame the clip sequence, while each subtitle file still needs to be checked against its own source.

Render a short offline example

Once the build and source files are verified, apply the filter to a short test render before attempting a continuous broadcast. A basic illustrative pattern is:

ffmpeg -i input.mp4 -vf "subtitles=subtitles.srt" -c:v libx264 -c:a copy output.mp4

This command shows the rendering step only. It assumes the input file, an external SRT file, a build with the filter, an available libx264 encoder and an audio stream that can be copied into the chosen output container. It has not specified a playlist, YouTube Live destination, live output format or account-specific settings, and should not be treated as a complete streaming command.

The -vf option applies a video filter; the subtitles filter draws text onto video frames. Since the pixels change, the video must be encoded again. Video stream copy (-c:v copy) skips decoding, filtering and encoding, so it cannot preserve an applied visual filter. This is a basic mechanical constraint, not a preference that can be fixed with a different subtitle option.

Audio is different. The example copies audio rather than re-encoding it, which can be convenient when the codec and container are compatible. But it is only an assumption for the example. If the source audio format is not accepted by your output path, you must choose an appropriate audio encoding or container. Likewise, libx264 is one possible encoder name, not a guarantee that it exists in the particular FFmpeg build.

Render a short portion first, then play the output in an ordinary player. Confirm that text appears and that the picture and sound remain in sync. A successful command is not proof that the captions are legible at the intended stream resolution or that YouTube will accept the later live configuration.

Encode filtered video for YouTube Live

The offline output and a live encoder output have different jobs. For YouTube Live, FFmpeg must encode the filtered frames and send an audio/video stream to the ingest destination configured for the channel. The destination URL and stream key come from the channel’s live setup; keep the key private and do not paste it into public scripts, screenshots or a support post.

Consult YouTube’s current live encoder settings, bitrates and resolutions for the stream you are preparing, and its instructions for creating a live stream with an encoder for the channel-side steps. Those pages are the reference for the settings and destination exposed to your account. A command that works for one output mode, resolution or account setup should not be copied blindly as a universal configuration.

Filtering means your video is being decoded, processed and encoded continuously. The workload depends on the source, output settings, encoder and machine; there is no universal hardware minimum established here. In practice, render and test a representative clip at the resolution you plan to send. If encoding cannot keep pace, a live output can lag or fail to maintain the intended cadence. Lowering output resolution or choosing a suitable encoder may help, but test the actual configuration rather than assuming a preset is adequate.

There is a trade-off between preparing files in advance and rendering during the stream. Pre-rendering hard subtitles gives you a finished clip to inspect and avoids repeating subtitle rendering at live time, but changes to wording or timing mean you must render that clip again. Applying the filter in a continuous process keeps the source media intact, but requires the running process to select the correct subtitle for every clip and to encode reliably for as long as the broadcast runs.

If the particular pain is keeping a continuous broadcast running while your own computer is off, StreamNeo addresses that operational burden by turning an uploaded video into a YouTube live stream that can be monitored and restarted if it drops. It does not change the caption trade-off: text already burned into the video remains part of the picture, and you should still prepare and inspect the media you upload.

Adapt the render for a playlist

“Playlist” can mean several different outputs. A local list of clips played one after another into a single live encoder process is not the same as a YouTube playlist of published videos, nor is either one the same as creating an HLS playlist file. FFmpeg documents HLS output and subtitle renditions in its formats documentation, but producing HLS does not itself send a feed to YouTube Live.

For a local sequence with separate subtitle files, each clip needs the matching text and timing. A simple one-file render does not describe how to advance to the next clip, handle different frame sizes, preserve audio continuity, repeat the list, or recover after a source is missing. Those are playlist orchestration decisions. Define them separately, and verify how your chosen player or script passes the correct subtitle source when the input changes.

Two broad approaches are common. You can render each clip with its own subtitles before assembling the sequence, or apply the filter within a continuous playback and encoding workflow. Pre-rendering allows you to inspect the final file individually and makes the playlist stage less dependent on subtitle selection. It also creates extra output files and means a corrected cue requires another render. Filtering in the live process avoids a separate rendered copy, but increases the complexity of the stream process and its ongoing compute demand.

Approach Useful when What to plan for
Render clips individually first You want to check each finished clip before scheduling it Correct pairing, consistent output settings, storage and re-rendering edits
Filter during continuous playback You need a single process to handle source clips and output Per-clip subtitle selection, clip boundaries, sustained encoding and recovery behaviour
Publish videos, then make a YouTube playlist Viewers should select among published videos This is not one continuous live encoder feed

If you want to send pre-encoded video without changing its frames, a copy-mode workflow may be relevant, but it is incompatible with burning new subtitles at that stage. The difference is explained in the guide to streaming a pre-encoded H.264 playlist with FFmpeg copy mode. Use it to understand the alternative, not as a way to bypass re-encoding after adding text.

Test timing, appearance and stream output

Review subtitles at the final output dimensions, not just on a large editing monitor. Text that looks clear on a laptop can become small on a phone or be obscured by channel graphics. Check safe placement near the lower edge, line breaks, contrast against bright footage and any overlap with on-screen titles. ASS files can carry styling, while appearance from other subtitle formats depends on the selected rendering behaviour and available fonts.

Check timing at the beginning, middle and end of each clip, and around edits or repeated sections. If a clip has been trimmed, sped up or joined to another, its subtitle timestamps may no longer match. Verify language and spelling against the audio rather than assuming the filename proves the contents. A brief test of one clip does not validate every file in a large playlist.

Then test the output at the intended live resolution and with the intended audio/video settings. Use YouTube’s live control room and encoder instructions for the channel-side checks. Confirm that the live feed arrives, that text is visible at the expected size, and that audio remains in sync. If you are building a recurring 24/7 setup, power continuity also matters; the practical considerations in the power backup guide for a 24/7 YouTube PC are relevant when the encoder depends on a local machine.

When something fails, isolate the layer. Missing filter means inspect build support and libass. Missing or incorrect text means check paths, embedded stream selection, language and file pairing. An output that renders but is slow points to the cost of filtering and encoding, which varies with source and settings. A stream that YouTube does not receive calls for checking the current encoder setup and the destination settings in the channel, rather than changing subtitle cues at random.

Before committing, compare the operating options on the pricing page. When the file and channel are ready, start free — 24-hour trial, no card.

FAQ

Can viewers turn off subtitles burned in with FFmpeg?

No. The subtitle text is rendered into the video image, so it is not a separate caption track and cannot be switched off as one. If viewers need control or language choice, provide a separate caption track through the appropriate YouTube workflow.

Why does FFmpeg say there is no subtitles filter?

The executable you are using may not include the filter or libass support. Check the filter list and build configuration, then use a build configured with libass and verify that your actual script or scheduled job calls that executable.

Can I burn subtitles and use video copy mode?

No. Burning subtitles changes the frames, and video stream copy bypasses the decoding, filtering and encoding needed to make that change. Encode the video after applying the filter; audio may still be copied only when its format is compatible with the output.

Is the offline command a complete YouTube playlist stream?

No. It demonstrates a single-file subtitle render and does not define playlist handling or the live ingest configuration. Decide whether you mean a local sequence of clips, a YouTube playlist of published videos or an HLS output, then follow the relevant FFmpeg and YouTube instructions for that workflow.

YOU’VE REACHED THE END

Keep the ideas coming.

More guides, useful tools and a little help for your next broadcast.

Back to the journal ↗
YOUR NEXT READ

A little more to explore.

More Setup Guides guides ↗ · All topics ↗