Font Face
Teva Sans Latin

Drafts & Templates
PBS Templates

Primitives & components context

Primitives & components: Teva SCS

Video - Modal

v0.0.0

Use data attribute data-player-mode="modal" to use the modal mode of the Vision Video Player.

When in modal mode, the Vision Video Player is displayed as a play button wrapping an image. When clicked a modal with the video appears.

One big advantage of this mode is that the aspect ratio can differ from that of the video.

<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-google-key="AIzaSyCCT69wewvdxKePFXN40xeJmy5MQusd9uc" data-player-mode="modal" data-video-id="PiVcDIRF3V4" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="youtube" role="button" tabindex="0">
  <!-- / allow different aspect ratio -->
  ...
</div>

Following data-attributes are required:

  • data-video-id to set the video id.
  • data-video-provider to set the video provider [youtube|vimeo].
  • data-google-key is required use the embed player API from google*

* No key is needed to use vimeo player API.

Instead of using data-google-key on every Vision Video Player, the key can also be set by creating a meta tag: <meta name="google-key" id="google-key" content="the-key-xyz" />

Following data-attributes are optional:

  • data-video-title to set a custom title on the video modal.
  • data-video-description-id to set id to the description part of the video modal.
  • data-video-modal-close-button-label when modal is used, it sets the label of the modals close button.
  • data-video-lazy when true the video loads lazily. (but will need a click on the vendor player)

Poster #

To use the default video poster from YouTube or Vimeo add a div with class .vi-video__poster inside a Rectangular Image with video aspect ratio instead of an image.


<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-google-key="AIzaSyCCT69wewvdxKePFXN40xeJmy5MQusd9uc" data-player-mode="modal" data-video-id="PiVcDIRF3V4" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="youtube" role="button" tabindex="0">
  <!-- Rectangular Image (mods: --video) -->
  <div class="vi-rectangular-image vi-rectangular-image--video">
    <div class="vi-video__poster"></div>
  </div>
</div>
<hr>
<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-player-mode="modal" data-video-id="65107797" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="vimeo" role="button" tabindex="0">
  <!-- Rectangular Image (mods: --video) -->
  <div class="vi-rectangular-image vi-rectangular-image--video">
    <div class="vi-video__poster"></div>
  </div>
</div>

The following example shows a poster inside Rectangular Image with a strip-hero aspect ratio
So this is not 16:9 aspect ratio.

<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-player-mode="modal" data-video-id="65107797" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="vimeo" role="button" tabindex="0">
  <!-- / allow different aspect ratio -->
  <!-- Rectangular Image (mods: --strip-hero) -->
  <div class="vi-rectangular-image vi-rectangular-image--strip-hero">
    <div class="vi-video__poster"></div>
  </div>
</div>

Visual #

To use a custom visual, use Rectangular Image with video aspect ratio.

alt text

alt text
<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-google-key="AIzaSyCCT69wewvdxKePFXN40xeJmy5MQusd9uc" data-player-mode="modal" data-video-id="PiVcDIRF3V4" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="youtube" role="button" tabindex="0">
  <!-- Rectangular Image (mods: --video) -->
  <div class="vi-rectangular-image vi-rectangular-image--video"><img alt="alt text" draggable="false" loading="lazy" src="/assets/images/static/test-1038x584.jpg"></div>
</div>
<hr>
<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-player-mode="modal" data-video-id="65107797" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="vimeo" role="button" tabindex="0">
  <!-- Rectangular Image (mods: --video) -->
  <div class="vi-rectangular-image vi-rectangular-image--video"><img alt="alt text" draggable="false" loading="lazy" src="/assets/images/static/test-1038x584.jpg"></div>
</div>

The following example shows a visual inside Rectangular Image with a strip-hero aspect ratio
So this is not 16:9 aspect ratio.

alt text
<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-player-mode="modal" data-video-id="65107797" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="vimeo" role="button" tabindex="0">
  <!-- / allow different aspect ratio -->
  <!-- Rectangular Image (mods: --strip-hero) -->
  <div class="vi-rectangular-image vi-rectangular-image--strip-hero"><picture>
      <source media="(max-width:767px)" srcset="/assets/images/static/test-360x360.jpg, /assets/images/static/test-720x720.jpg 2x">
      <source media="(max-width:959px)" srcset="/assets/images/static/test-768x470.jpg, /assets/images/static/test-1536x940.jpg 2x">
      <img alt="alt text" draggable="false" loading="lazy" src="/assets/images/static/test-910x530.jpg" srcset="/assets/images/static/test-910x530.jpg, /assets/images/static/test-1820x1060.jpg 2x">
    </picture></div>
</div>

The reference button #

Use the reference button when the video player is already somewhere in the markup. This prevents to much video instantiations.

Simply point the href attribute of the button (link) to the id of the video.

<!-- Button type: solid  -->
<a aria-label="Open and play the video in a dialog window." href="#sg-80825c" role="button" class="vi-btn-solid vi-btn-solid--no-pointer vi-btn-solid--accent-1 vi-btn">Tofu cray
  <!-- Icon video-play (mods: --button-end) -->
  <svg xmlns="http://www.w3.org/2000/svg" viewbox="0 0 12 12" sg-icons-dir="sg/components/icon/icons" role="img" class="vi-icon vi-icon--button-end" aria-label="video-play" width="12" height="12"><path d="M11.1 5.4c.5.3.5.8 0 1.1l-7.3 4.9c-.4.3-.8.1-.8-.5V1c0-.5.4-.7.8-.4l7.3 4.8z" fill-rule="evenodd"></path></svg></a>
<hr>
<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-player-mode="modal" data-video-id="65107797" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="vimeo" id="sg-80825c" role="button" tabindex="0">
  <!-- Rectangular Image (mods: --video) -->
  <div class="vi-rectangular-image vi-rectangular-image--video">
    <div class="vi-video__poster"></div>
  </div>
</div>

Description #

To add a description we use a hidden Modal Layout somewhere on the page.

The data-video-description-id must correspond with the id of the Modal Layout.

The custom title of the modal is set with data-video-title.

Synth authentic williamsburg.

Direct trade organic forage vice typewriter. Seitan diy 90's taxidermy listicle ethical bespoke. Leggings tousled fixie kale chips sustainable green juice.

<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-google-key="AIzaSyCCT69wewvdxKePFXN40xeJmy5MQusd9uc" data-player-mode="modal" data-video-description-id="sg-1c74a6" data-video-id="PiVcDIRF3V4" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="youtube" data-video-title="Custom modal title above the video" role="button" tabindex="0">
  <!-- / allow different aspect ratio -->
  ...
</div>
<!-- .d-none is Bootstrap display none class -->
<div class="d-none">
  <!-- Modal Layout  -->
  <div class="vi-modal-layout" id="sg-1c74a6">
    <div class="vi-modal-layout__body">
      <div class="vi-modal-layout__section">
        <div class="vi-typesystem">
          <h3>Synth authentic williamsburg.</h3>
        </div>
      </div>
      <div class="vi-modal-layout__section">
        <div class="vi-typesystem vi-typesystem--collapse-last">
          <p>Direct trade organic forage vice typewriter. Seitan diy 90's taxidermy listicle ethical bespoke. Leggings tousled fixie kale chips sustainable green juice.</p>
        </div>
      </div>
    </div>
  </div>
</div>

Lazy loaded video #

Where data-video-lazy is set to true.


<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-google-key="AIzaSyCCT69wewvdxKePFXN40xeJmy5MQusd9uc" data-player-mode="modal" data-video-id="PiVcDIRF3V4" data-video-lazy="true" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="youtube" role="button" tabindex="0">
  <!-- Rectangular Image (mods: --video) -->
  <div class="vi-rectangular-image vi-rectangular-image--video">
    <div class="vi-video__poster"></div>
  </div>
</div>
<hr>
<!-- Video  -->
<div class="vi-video" data-aria-label="Open and play the video in a dialog window." data-player-mode="modal" data-video-id="65107797" data-video-lazy="true" data-video-modal-close-button-label="Video modal dialog, click to close, or navigate to the video clip playing." data-video-provider="vimeo" role="button" tabindex="0">
  <!-- Rectangular Image (mods: --video) -->
  <div class="vi-rectangular-image vi-rectangular-image--video">
    <div class="vi-video__poster"></div>
  </div>
</div>

Stylesheets #

The following stylesheets are required to display this component.


JavaScript #

The following javascripts are required to display this component.


Usage documentation #

Usage documentation can be found here.


Changelog #

Changelog

Changed

  • 13 Aug 2025 - fix(video): fix inline video scroll offset calculation
  • 10 Juni 2024 - Use youtube-nocookie.com for youtube videos.
  • 04 Juli 2022 - Transcript default is ‘open’
  • A11y add enter/space to trigger video.
  • Try to autoplay lazy-loaded videos (only works when browser allows it)
  • Update javascript to push custom message to GTM dataLayer.
  • PBS support tweak to better support biosimilars theme
  • Pause on audio play
  • Update to new Vimeo oEmbed API
  • A modifier class --modal used by js was renamed --button. Make sure that js AND css are updated.
  • Refactor Mode: Background
  • Refactor Mode: Button
  • Print: css adjustments
  • Pause autoplay when playing video in slider.
  • Override onYouTubeIframeAPIReady when defined to prevent conflict with googletagmanager. Also works in IE11
  • Accessibility: return focus on initiating element.
  • Accessibility: added data-attribute data-video-modal-close-button-label to set the aria-label of the close button. Contents of button changed to X because we use an aria-label.
  • Accessibility: Video, add role and aria-label to video component.
  • Switch between ‘inline’ and ‘modal’ mode from 768px to 960px.

Fix

  • 11 Nov 2024 - fix(video): call to undefined modal
  • 14 May 2024 - Fix for lazy loaded videos playing after closing modals before video load.
  • 13 Sep 2023 - Try to fix unreproducable pause bug in video collection.
  • 11 Aug 2022 - Fix transcript content padding in documentation.
  • 12 Juli 2022 - Trigger dom change after cloning description.
  • 28 June 2022 - Fix scrollparent detector
  • Youtube background shows as 1px black line when video mode background
  • Fix rounding issue artificial object fit.
  • Fix autoplay lazy-loaded videos: hybrid mode should not autoplay when vendor embed is displayed (small screens).
  • Background Video GTM dataLayer error.
  • Stop Video Component correctly when modal is closed.
  • Scroll issue in inline mode.
  • YT Inline mode not playing in place on iOS.
  • Fix the handling of ‘external’ clicks towards cloned elements in slider.
  • Temporary Fix ‘Vimeo makes incorrect jsonp callback’ when the name of the callback starts with ‘jQuery’ (!?)
  • Slider change interference causing video pause.
  • Do not require youtube key for vimeo videos.
  • Object fit calculation not always correct.
  • Background mode creates modal on incoming links.

Added

  • 20 June 2022 - Documentation on the use of Transcripts
  • Optional data-video-poster option, to disable the poster image on a background video.
  • Add data-player-mode="button" to allow button mode on any link or button element.
  • Optional data-video-lazy option, to lazy load vendor player.
  • PBS support
  • Mode: Inline
  • Mode: Modal
  • Add data attribute data-video-description-id to point to description. Works for Video as wel as for Video Button
  • Video Button with documentation.
  • Background video examples
  • Initial draft