If you host video on your own site, in a course platform, or in a web app, the subtitles have to be WebVTT. It is the only format the HTML5 <track> element understands. ToneLark produces a VTT file from any video or audio upload, timed to the speech, ready to drop next to your MP4.

How to get a VTT file for your video

  1. Create a free account and upload the video or audio (up to 2 GB).
  2. Wait for the email. The spoken language is detected automatically and the speech is transcribed with timecodes.
  3. Download the VTT file. An SRT is produced as well, in case the same video goes to YouTube or an editor.

Add the track to your player

Place the VTT file on your server and reference it from the video element:

<video controls preload="metadata">
  <source src="/media/talk.mp4" type="video/mp4" />
  <track
    kind="subtitles"
    src="/media/talk.vtt"
    srclang="en"
    label="English"
    default
  />
</video>
  • kind="subtitles" is for the spoken dialogue; use kind="captions" when the file also describes sounds for viewers who cannot hear the audio.
  • srclang is the language code of the text, label is what the viewer sees in the menu.
  • default turns the track on without the viewer having to pick it. Leave it off if you want captions opt-in.

Several <track> elements can sit on one video, one per language.

What a WebVTT file contains

WEBVTT

00:00:01.000 --> 00:00:03.500
Welcome, and thanks for joining.

00:00:03.600 --> 00:00:06.000
Let's start with the basics.

The header line, a blank line, then cues with a dot before the milliseconds. Cue identifiers are optional. For the full comparison with SRT, see SRT vs VTT.

Why captions sometimes do not appear

These are the things to check, in order:

  1. Content type. The file must be served as text/vtt. Some servers send .vtt as text/plain or application/octet-stream, and browsers ignore it.
  2. Same origin, or CORS. If the VTT lives on a different domain or CDN than the page, the response needs an Access-Control-Allow-Origin header and the video element needs crossorigin="anonymous".
  3. The header. The first line must be exactly WEBVTT. A byte-order mark or a stray space before it breaks the file in some browsers.
  4. Commas in timestamps. A comma instead of a dot makes the browser drop that cue.
  5. Track switched off. Without default, the viewer has to enable captions from the player menu.

Styling the captions

Basic styling works from CSS:

video::cue {
  font-size: 1.1rem;
  background: rgba(0, 0, 0, 0.75);
  color: #fff;
}

Position, alignment and size can also be set per cue inside the VTT file, and spans of text can be tagged with <c.classname> for finer control. Support varies between browsers, so test the ones your audience uses.

Keep the timing right

The VTT file is timed to the exact file you upload. If you later trim or re-encode the video at a different speed, generate a new file rather than editing cues by hand. If you inherit a file that drifts, how to fix out-of-sync subtitles covers the repair.

Pricing

10 free minutes of transcription per calendar month, no card. Prepaid minute packs for more, valid for 12 months. Files are deleted automatically after about a day, so download the VTT when the email arrives.