How do I color cues on webvtt?

814 views Asked by At

HTML

<!DOCTYPE HTML>
<html>
  <head>
    <link rel="stylesheet" href="styles.css">
  </head>
  <body>
    <video controls autoplay>
      <source src="./test.mp4" type="video/mp4"/>
      <track default kind="captions" srclang="en" label="English" src="./test.vtt"/>
    </video>
  </body>
</html>

CSS

.yellowish {
  background-color: blue;
  color: yellow;
}
.redcolor {
  background-color: white;
  color: red;
}

VTT

WEBVTT

00:00:00.000 --> 00:00:03.000
<c.yellowish>This text should be yellow.</c> This text will be the default color.

00:00:03.000 --> 00:00:06.000
<c.redcolor>This text should be red.</c> This text will be the default color.

I hosted them on a simple http server with node.js and tried it on chromium and Firefox. They did not show colors. I tried including styles in the vtt file, it did not work either. Size and colors seems to be not working in Firefox and chromium. Alignment doesn't work in chromium. All other webvtt features work perfectly. Am I supposed to use any front-end frameworks for this? It works on YouTube perfectly.(1:30 to 1:40)

1

There are 1 answers

2
Carson On BEST ANSWER

Changing the CSS as below will work.

/* .yellowish { */
video::cue(.yellowish) {
  background-color: blue;
  color: yellow;
}
/* .redcolor { */
video::cue(.redcolor ) {
  background-color: white;
  color: red;
}

Example

<style>
  video::cue(.yellowish) {
    background-color: blue;
    color: yellow;
  }
  video::cue(.redcolor ) {
    background-color: white;
    color: red;
  }
</style>

<script>
  const vttTxt = `WEBVTT
00:00:00.000 --> 00:00:03.000
<c.yellowish>This text should be yellow.</c> This text will be the default color.

00:00:03.000 --> 00:09:56.000
<c.redcolor>This text should be red.</c> This text will be the default color.
`
  const blobVTT = new Blob([vttTxt], {"type": "text/plain"})
  const trackUrl = URL.createObjectURL(blobVTT)
  const frag = document.createRange().createContextualFragment(`
          <video width="400" height="200" controls>
  <source src="http://commondatastorage.googleapis.com/gtv-videos-bucket/sample/BigBuckBunny.mp4" type="video/mp4">
  <track src="${trackUrl}" kind="captions" srclang="en" label="English" default >
  </video>
          `)
  document.body.append(frag)
</script>


The following content is a suggestion, I do not recommend putting foreground and background colors together. According to the documentation.#default-classes, you can define attributes for individual colors separately, which will provide more flexibility when using them. Here is an example:

<style>
  /* color */
  video::cue(.yellow) {
    color: yellow;
  }
  video::cue(.bg_yellow) {
    background-color: yellow;
  }
  video::cue(.red) {
    color: red;
  }
  video::cue(.bg_red) {
    background-color: red;
  }

  /* font-size */
  video::cue(.big) {
    font-size: 2rem;
  }
</style>
00:00:00.000 --> 00:00:03.000
<c.yellow.bg_red>This text should be yellow.</c> This text will be the default color.

00:00:03.000 --> 00:09:56.000
<c.big.red.bg_yello>This text should be red.</c> This text will be the default color.

Example2

<style>
  video::cue(.yellow) {
    color: yellow;
  }
  video::cue(.bg_yellow) {
    background-color: yellow;
  }
  video::cue(.red) {
    color: red;
  }
  video::cue(.bg_red) {
    background-color: red;
  }
  video::cue(.big) {
    font-size: 2rem;
  }
</style>

<script>
const vttTxt = `WEBVTT
00:00:00.000 --> 00:00:03.000
<c.yellow.bg_red>This text should be yellow.</c> This text will be the default color.

00:00:03.000 --> 00:09:56.000
<c.big.red.bg_yellow>This text should be red.</c> This text will be the default color.
`
const blobVTT = new Blob([vttTxt], {"type": "text/plain"})
const trackUrl = URL.createObjectURL(blobVTT)
const frag = document.createRange().createContextualFragment(`
          <video width="400" height="200" controls>
  <source src="http://commondatastorage.googleapis.com/gtv-videos-bucket/sample/BigBuckBunny.mp4" type="video/mp4">
  <track src="${trackUrl}" kind="captions" srclang="en" label="English" default >
  </video>
          `)
document.body.append(frag)
</script>