{"version":3,"file":"js/8783-9905e049638f53e00cc8.chunk.js","mappings":"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","sources":["webpack://endrun/./app/javascript/app/video/video-js-caption-toggle.js","webpack://endrun/./app/javascript/app/video/video-js-tmp-play-btn.js","webpack://endrun/./app/javascript/app/video/video-player.js"],"sourcesContent":["// packages\nimport videojs from 'video.js';\n\n/*\n * A button component for toggling captions on and off.\n */\n\nconst VjsButton = videojs.getComponent('Button');\n\nexport default class CaptionToggle extends VjsButton {\n constructor(player, options) {\n super(player, options);\n\n this.updateTrackList();\n this.on(player, 'captionstatechange', this.toggleDisplay);\n this.on(player, 'captionsrcchange', this.updateTrackList);\n }\n\n /**\n * Builds the default DOM `className`. Called in the Button class.\n */\n buildCSSClass() {\n return `vjs-caption-toggle ${super.buildCSSClass()}`;\n }\n\n /**\n * This gets called in the Button class when a `CaptionToggle` is \"clicked\". See\n * {@link ClickableComponent} for more detailed information on what a click can be.\n *\n * @listens tap\n * @listens click\n */\n handleClick() {\n this.toggleCaptions();\n }\n\n /*\n * Update textTrackList when caption src url is updated.\n */\n updateTrackList() {\n this.textTrackList = this.player().remoteTextTracks();\n }\n\n /*\n * Get caption visibility based on current textTrackList\n */\n getVisibilityState() {\n let track, trackMode;\n\n for (var i = 0; i < this.textTrackList.length; i++) {\n track = this.textTrackList[i];\n if (track.kind === 'captions') {\n trackMode = track.mode;\n break;\n }\n }\n\n return trackMode || 'disabled';\n }\n\n /**\n * Toggle the current caption state.\n */\n toggleCaptions() {\n // Get current state of caption visibility\n const captionState = this.getVisibilityState();\n let newState;\n\n if (captionState === 'showing') {\n newState = 'hidden';\n } else if (captionState === 'hidden') {\n newState = 'showing';\n }\n\n this.player().trigger('captionstatechange', {\n showCaptions: newState === 'showing',\n });\n }\n\n /**\n * Update the `CaptionToggle` button based on the state of caption visibility.\n */\n toggleDisplay(_, d) {\n const newState = d.showCaptions ? 'showing' : 'hidden';\n this.updateIcon(newState);\n this.updateControlText_(newState);\n }\n\n /**\n * Update styles on the `CaptionToggle` button based on the state of caption visibility.\n */\n updateIcon(captionState) {\n if (captionState === 'showing') {\n this.removeClass('vjs-disabled');\n this.addClass('vjs-selected');\n } else if (captionState === 'hidden') {\n this.removeClass('vjs-selected');\n this.removeClass('vjs-disabled');\n } else {\n this.addClass('vjs-disabled');\n }\n }\n\n /**\n * If caption visibility has changed on the player, update the control text\n * (`title` attribute on the element and content of\n * `vjs-control-text` element).\n */\n updateControlText_(captionState) {\n const text = captionState == 'showing' ? 'Hide captions' : 'Show captions';\n\n if (this.controlText() !== text) {\n this.controlText(text);\n }\n }\n}\n\n/**\n * The text that should display over the `CaptionToggle`s controls. Added for localization.\n *\n * @type {string}\n * @private\n */\nCaptionToggle.prototype.controlText_ = 'Show/hide captions';\n\nVjsButton.registerComponent('CaptionToggle', CaptionToggle);\n","import videojs from 'video.js';\n\n/*\n * A custom \"big play button\" that replaces the initial play button that shows\n * before a video has played.\n */\n\nconst Component = videojs.getComponent('Component');\nconst VjsBigPlayButton = videojs.getComponent('BigPlayButton');\n\nexport default class TMPBigPlayButton extends VjsBigPlayButton {\n constructor(player, options) {\n super(player, options);\n }\n\n\n buildCSSClass() {\n return 'vjs-big-play-button tmp-big-play-button';\n }\n\n\n createEl() {\n const tag = 'button';\n\n const props = {\n innerHTML: '',\n className: this.buildCSSClass()\n };\n\n const attributes = {\n type: 'button'\n };\n\n const el = Component.prototype.createEl.call(this, tag, props, attributes);\n\n this.createControlTextEl(el)\n\n return el;\n }\n}\n\nVjsBigPlayButton.registerComponent('TMPBigPlayButton', TMPBigPlayButton);\n","// packages\nimport defaults from 'underscore/modules/defaults.js';\nimport Hls from 'hls.js';\nimport { nanoid } from 'nanoid';\nimport videojs from 'video.js';\n\n// components\nimport './video-js-caption-toggle.js';\nimport './video-js-tmp-play-btn.js';\n\n// local\nimport { createEvent } from '../util/events.js';\n\nexport default class VideoPlayer {\n constructor(options) {\n /** @type {HTMLElement} */\n this.el = options.el;\n this.state = this.getInitialState(options);\n this.playerType = this.getPlayerType();\n this.render();\n this.initializeVideo();\n this.initializeEventListeners();\n }\n\n getInitialState(options) {\n const dataset = this.el.dataset;\n\n return defaults(\n options,\n {\n autoplay: dataset.autoplay,\n captionLang: dataset.captionLang,\n captionUrl: dataset.captionUrl,\n fullVideo: dataset.fullVideo,\n fallbackUrl: dataset.fallbackSrc,\n hasChrome: dataset.chrome,\n hlsUrl: dataset.src,\n id: this.el.id,\n inactivityTimeout: dataset.inactivityTimeout\n ? parseInt(dataset.inactivityTimeout, 10)\n : undefined,\n lazyLoad: dataset.lazyLoad,\n loop: dataset.loop,\n muted: dataset.muted,\n poster: dataset.poster,\n showCaptions: dataset.showCaptions,\n showRemainingTime: dataset.showRemainingTime,\n spanishCaptionUrl: dataset.esCaptionUrl,\n controlsTimeout: null,\n playerStartTime: 0,\n playerVolume: 1,\n vttSeparator: '
',\n containVideo: false,\n },\n {\n autoplay: false,\n captionLang: 'en',\n captionUrl: false,\n fullVideo: false,\n fallbackUrl: dataset.fallbackSrc,\n hasChrome: false,\n hlsUrl: dataset.src,\n id: nanoid(),\n inactivityTimeout: 1500,\n loop: false,\n muted: false,\n lazyLoad: true,\n showCaptions: false,\n showRemainingTime: true,\n spanishCaptionUrl: false,\n }\n );\n }\n\n resetStates() {\n // State values to reset when updating the video source but maintaining\n // a persistent player.\n this.state.captionUrl = null;\n this.state.spanishCaptionUrl = null;\n this.state.fallbackUrl = null;\n this.state.hlsUrl = null;\n this.state.videoHasLoaded = null;\n }\n\n render() {\n const renderedTemplate = this.template(this.templateData());\n this.el.innerHTML = renderedTemplate;\n this.resizeVideoContainer();\n }\n\n template(data) {\n let captionHTML = data.captionUrl\n ? ``\n : '';\n captionHTML += data.spanishCaptionUrl\n ? `\\n`\n : '';\n const html = `\n
\n \n
\n
\n `;\n\n return html;\n }\n\n templateData() {\n const videoProperties = [];\n if (this.state.muted) {\n videoProperties.push('muted');\n }\n\n if (this.state.loop) {\n videoProperties.push('loop');\n }\n\n if (this.state.autoplay) {\n videoProperties.push('autoplay');\n }\n\n if (this.state.poster) {\n videoProperties.push(`poster=\"${this.state.poster}\"`);\n }\n\n if (this.state.setup) {\n videoProperties.push(`data-setup=\"${this.state.setup}\"`);\n }\n\n if (this.state.fullVideo) {\n videoProperties.push('data-object-fit=\"cover\"');\n }\n\n const className = [];\n if (this.state.fullVideo) {\n className.push('full-frame-video');\n }\n\n return Object.assign(\n {\n videoProperties: videoProperties.join(' '),\n className: className.join(' '),\n },\n this.state\n );\n }\n\n resizeVideoContainer() {\n if (!this.state.containVideo) {\n return;\n }\n\n const windowHeight = window.innerHeight;\n const windowWidth = window.innerWidth;\n const aspectRatio = windowHeight / windowWidth;\n if (aspectRatio < 0.56) {\n // Standard aspect ratio for videos\n const videoWidth = windowHeight / 0.56;\n this.el.style.maxWidth = `${videoWidth}px`;\n }\n }\n\n getPlayerType() {\n // Use basic HTML5 video for Chromeless stuff\n // Because video.js's http streaming support does not like looping videos\n const checkVideo = document.createElement('video');\n if (!this.state.hasChrome) {\n if (Hls.isSupported() && this.state.hlsUrl.length) {\n // Somewhat unintuitively, this actually checks whether the hls.js library\n // is supported, not whether HLS is supported. Hls.js is supported where\n // Media Source Extensions are enabled.\n return 'html5-mse';\n } else if (\n checkVideo.canPlayType('application/vnd.apple.mpegurl') &&\n this.state.hlsUrl.length\n ) {\n // hls.js is not supported on platforms that do not have Media Source\n // Extensions (MSE) enabled. When the browser has built-in HLS support\n // (check using `canPlayType`), we can provide an HLS manifest (i.e.\n // .m3u8 URL) directly to the video element throught the `src` property.\n // This is using the built-in support of the plain video element, without\n // using hls.js.\n return 'html5-hls';\n } else {\n // In the case that neither HLS, nor MSE is supported (IE11 on Windows 7,\n // mostly) we fall back to the raw MP4.\n return 'html5-fallback';\n }\n } else {\n // If the video does have chrome, use video.js player, which comes with\n // handy interface options\n if (\n this.state.hlsUrl.length &&\n (Hls.isSupported() ||\n checkVideo.canPlayType('application/vnd.apple.mpegurl'))\n ) {\n // We use videojs-http-streaming to use HLS with browsers that support HLS\n // natively or support Media Source Extensions.\n return 'videojs-hls';\n } else {\n // In the case that neither HLS, nor MSE is supported (IE11 on Windows 7,\n // mostly) we fall back to the raw MP4.\n return 'videojs-fallback';\n }\n }\n }\n\n updateCaptionSrc() {\n if (this.jsPlayer) {\n const trackList = this.jsPlayer.remoteTextTracks();\n\n const tracksToRemove = [];\n for (var i = 0; i < trackList.length; i++) {\n if (trackList[i].kind === 'captions') {\n tracksToRemove.push(trackList[i]);\n }\n }\n\n tracksToRemove.forEach((track) => {\n this.jsPlayer.removeRemoteTextTrack(track);\n });\n\n if (this.state.captionUrl) {\n const addedTrack = this.jsPlayer.addRemoteTextTrack(\n {\n src: this.state.captionUrl,\n kind: 'captions',\n srclang: 'en',\n label: 'English',\n mode:\n this.state.showCaptions && this.state.captionLang === 'en'\n ? 'showing'\n : 'hidden',\n },\n true\n );\n\n addedTrack.addEventListener('load', () => {\n this.jsPlayer.trigger('captionsrcchange');\n });\n }\n\n if (this.state.spanishCaptionUrl) {\n const addedSpanishTrack = this.jsPlayer.addRemoteTextTrack(\n {\n src: this.state.spanishCaptionUrl,\n kind: 'captions',\n srclang: 'es',\n label: 'Spanish',\n mode:\n this.state.showCaptions && this.state.captionLang === 'es'\n ? 'showing'\n : 'hidden',\n },\n true\n );\n\n addedSpanishTrack.addEventListener('load', () => {\n this.jsPlayer.trigger('captionsrcchange');\n });\n }\n\n if (!this.state.captionUrl && !this.state.spanishCaptionUrl) {\n this.jsPlayer.trigger('captionsrcchange');\n }\n }\n }\n\n setVideoSrc(srcData) {\n // If we are passing updated data\n if (srcData) {\n this.resetStates();\n const updatedData = defaults(srcData || {}, this.state);\n this.state = updatedData;\n this.updateCaptionSrc();\n }\n\n if (this.playerType === 'html5-mse') {\n this.hls.loadSource(this.state.hlsUrl);\n this.hls.attachMedia(this.videoEl);\n } else if (this.playerType === 'html5-hls') {\n this.videoEl.src = this.state.hlsUrl;\n } else if (this.playerType === 'html5-fallback') {\n this.videoEl.src = this.state.fallbackUrl;\n } else {\n if (this.playerType === 'videojs-hls') {\n this.jsPlayer.src({\n src: this.state.hlsUrl,\n type: 'application/x-mpegURL',\n });\n } else {\n this.jsPlayer.src({\n src: this.state.fallbackUrl,\n type: 'video/mp4',\n });\n }\n }\n }\n\n initializeVideo() {\n window.VIDEOJS_NO_DYNAMIC_STYLE = true;\n this.videoEl = this.el.querySelector('video');\n\n if (this.playerType === 'html5-mse') {\n this.hls = new Hls({ autoStartLoad: !this.state.lazyLoad });\n this.setVideoSrc();\n this.hls.on(Hls.Events.MANIFEST_PARSED, () => {\n this.videoReady();\n });\n\n this.supportedPlayer = this.videoEl;\n } else if (\n this.playerType === 'html5-hls' ||\n this.playerType === 'html5-fallback'\n ) {\n this.setVideoSrc();\n this.videoEl.addEventListener('loadedmetadata', () => {\n this.videoReady();\n });\n\n this.supportedPlayer = this.videoEl;\n } else {\n const controlBarComponents = this.getControlBarComponents();\n\n this.jsPlayer = videojs(this.videoEl, {\n controls: this.state.hasChrome,\n preload: 'metadata',\n inactivityTimeout: this.state.inactivityTimeout,\n textTrackSettings: false,\n controlBar: {\n children: controlBarComponents,\n },\n html5: {\n hls: {\n overrideNative: false,\n },\n },\n });\n\n // Replace the default BigPlayButton with a custom TMP button\n this.jsPlayer.removeChild('BigPlayButton');\n this.jsPlayer.addChild('TMPBigPlayButton');\n\n this.setVideoSrc();\n this.supportedPlayer = this.jsPlayer;\n this.jsPlayer.ready(() => {\n this.videoReady();\n });\n\n // Trigger global mute event when player is muted or unmuted\n this.jsPlayer.on('volumechange', () => {\n const stateAfterChange = this.jsPlayer.muted();\n if (stateAfterChange) {\n window.dispatchEvent(createEvent('tmpaudio-mute'));\n } else {\n window.dispatchEvent(createEvent('tmpaudio-unmute'));\n }\n });\n }\n }\n\n getControlBarComponents() {\n const componentsInOrder = ['playToggle', 'muteToggle'];\n const numCaptions = [\n this.state.captionUrl,\n this.state.spanishCaptionUrl,\n ].filter(Boolean).length;\n\n if (numCaptions > 0) {\n const captionsPlugin =\n numCaptions > 1 ? 'CaptionsButton' : 'CaptionToggle';\n componentsInOrder.push(captionsPlugin);\n }\n\n componentsInOrder.push('progressControl');\n\n if (this.state.showRemainingTime) {\n componentsInOrder.push('remainingTimeDisplay');\n }\n\n componentsInOrder.push('fullscreenToggle');\n\n return componentsInOrder;\n }\n\n // Helper functions to streamline use of the two player types. Video.js\n // properties are all accessed through function calls, unlike native video.\n getPlayerProperty(propName) {\n if (this.jsPlayer) {\n return this.jsPlayer[propName]();\n } else {\n return this.videoEl[propName];\n }\n }\n\n setPlayerProperty(propName, arg) {\n if (this.jsPlayer) {\n this.jsPlayer[propName](arg);\n } else {\n this.videoEl[propName] = arg;\n }\n }\n\n onPlayerEvent(eventName, callback) {\n if (this.jsPlayer) {\n this.jsPlayer.on(eventName, callback);\n } else {\n this.videoEl.addEventListener(eventName, callback);\n }\n }\n\n offPlayerEvent(eventName, callback) {\n if (this.jsPlayer) {\n this.jsPlayer.off(eventName, callback);\n } else {\n this.videoEl.removeEventListener(eventName, callback);\n }\n }\n\n onePlayerEvent(eventName, callback) {\n if (this.jsPlayer) {\n this.jsPlayer.one(eventName, callback);\n } else {\n this.videoEl.addEventListener(\n eventName,\n (...args) => {\n callback(...args);\n },\n { once: true }\n );\n }\n }\n\n initializeEventListeners() {\n // Wait until file has loaded metadata, then get duration\n this.onPlayerEvent('loadedmetadata', (e) => {\n this.state.duration = this.getPlayerProperty('duration');\n this.setPlayerProperty('currentTime', this.state.playerStartTime);\n // Set boolean for checking if video is ready to be played\n this.state.videoHasLoaded = true;\n });\n\n this.onPlayerEvent('canplay', () => {\n this.videoCanPlay();\n });\n\n this.onPlayerEvent('captionstatechange', (e, d) => {\n if (d.showCaptions) {\n this.showCaptions();\n } else {\n this.hideCaptions();\n }\n });\n\n const videoItemFallback = this.el.querySelector('.video-item-fallback');\n\n videoItemFallback.addEventListener('click', () => {\n this.playVideo();\n\n videoItemFallback.classList.add('video-item-fallback-started');\n });\n\n window.addEventListener('tmpaudio-capture-autoplay-permission', () => {\n // Trigger an unmuted play in response to a gesture, so we lock in the\n // permission to play with sound. We have to do this for each video\n // element in turn because permission (on mobile) is granted on a\n // per-element basis.\n window.dispatchEvent(createEvent('tmpaudio-unmute'));\n const isNotAlreadyPlaying = this.getPlayerProperty('paused');\n\n this.supportedPlayer.play().then(() => {\n if (isNotAlreadyPlaying) {\n this.supportedPlayer.pause();\n }\n });\n });\n\n // Set event listener for global mute and unmute\n window.addEventListener('tmpaudio-mute', () => {\n this.setPlayerProperty('muted', true);\n if (this.jsPlayer) {\n this.jsPlayer.trigger('captionstatechange', { showCaptions: true });\n }\n });\n\n window.addEventListener('tmpaudio-unmute', () => {\n this.setPlayerProperty('muted', false);\n if (this.jsPlayer) {\n this.jsPlayer.trigger('captionstatechange', { showCaptions: false });\n }\n });\n\n window.addEventListener('tmp_resize', () => {\n this.resizeVideoContainer();\n });\n\n document.addEventListener('visibilitychange', () => {\n if (document.visibilityState === 'hidden') {\n this.pauseVideo();\n }\n });\n }\n\n // Start downloading the video\n startLoad() {\n if (this.jsPlayer) {\n } else if (this.hls) {\n this.hls.startLoad();\n }\n }\n\n // Stop downloading\n stopLoad() {\n if (this.jsPlayer) {\n } else if (this.hls) {\n this.hls.stopLoad();\n }\n }\n\n showCaptions() {\n if (this.jsPlayer) {\n const tracks = this.jsPlayer.remoteTextTracks();\n\n for (let idx = 0; idx < tracks.length; idx++) {\n const track = tracks[idx];\n\n if (\n track.kind === 'captions' &&\n track.language === this.state.captionLang\n ) {\n track.mode = 'showing';\n }\n }\n\n this.state.showCaptions = true;\n }\n }\n\n hideCaptions() {\n if (this.jsPlayer) {\n const tracks = this.jsPlayer.remoteTextTracks();\n\n for (let idx = 0; idx < tracks.length; idx++) {\n const track = tracks[idx];\n\n if (track.kind === 'captions') {\n track.mode = 'hidden';\n }\n }\n\n this.state.showCaptions = false;\n }\n }\n\n // Detect whether video is playing\n getPlayState() {\n if (this.getPlayerProperty('paused') || this.getPlayerProperty('ended')) {\n return 'paused';\n } else if (this.getPlayerProperty('readyState') < 4) {\n return 'notready';\n }\n return 'playing';\n }\n\n // Play the video.\n playVideo(options = { enableFades: false }) {\n // Because we can't animate volume through the video-js API, we use jQuery\n // to animate the volume level on the DOM element itself.\n // jQuery.stop() clears the animation queue from previous fades.\n // Disabling fades for now until we have a use-case, hard to recreate without\n // jQuery.\n // $(this.videoEl).stop();\n\n if (this.getPlayState() === 'playing') {\n return;\n }\n\n // Options include the boolean enableFades, which defaults to false.\n // const { enableFades } = options;\n\n // By default, play/pause will start or stop the video immediately.\n // If enableFades == true, the video will play/pause with a brief fade in or out.\n // if (enableFades) {\n // this.setPlayerProperty('volume', 0);\n // }\n\n const playPromise = this.supportedPlayer.play();\n //const playPromise = Promise.reject(new Error('test'));\n\n const handleSuccessfulPlay = () => {\n if (this.jsPlayer) {\n this.jsPlayer.trigger('captionstatechange', {\n showCaptions: this.state.showCaptions,\n });\n }\n\n const videoItemFallback = this.el.querySelector('.video-item-fallback');\n videoItemFallback.classList.add('video-item-fallback-started');\n\n // if (enableFades) {\n // $(this.videoEl).animate({ volume: this.state.playerVolume }, 1000);\n // }\n };\n\n if (playPromise !== undefined) {\n playPromise.then(handleSuccessfulPlay).catch((error) => {\n console.log(\n error,\n 'Not allowed to autoplay with sound, muting and retrying'\n );\n window.dispatchEvent(createEvent('tmpaudio-mute'));\n\n this.supportedPlayer\n .play()\n //Promise.reject(new Error('test'))\n .then(handleSuccessfulPlay)\n .catch(() => {\n this.showPlayerFallback();\n });\n });\n } else {\n handleSuccessfulPlay();\n }\n }\n\n // Pause the video.\n pauseVideo(options = { enableFades: false }) {\n // jQuery.stop() clears the animation queue from previous fades.\n // $(this.videoEl).stop();\n\n if (this.getPlayState() === 'paused') {\n return;\n }\n\n // Options include the boolean enableFades, which defaults to false.\n // const { enableFades } = options;\n\n // By default, play/pause will start or stop the video immediately.\n // If enableFades == true, the video will play/pause with a brief fade in or out.\n // if (enableFades) {\n // $(this.videoEl).animate({ volume: 0 }, 1000, (e) => {\n // // Wait until transition has finished before pausing\n // this.supportedPlayer.pause();\n // // Restore volume to previous level\n // this.setPlayerProperty('volume', this.state.playerVolume);\n // });\n // } else {\n this.supportedPlayer.pause();\n // }\n }\n\n // Toggle play/pause state\n togglePlay(options) {\n // Go from paused to playing\n if (this.getPlayState() == 'paused') {\n this.playVideo(options);\n // Go from playing to paused\n } else {\n this.pauseVideo(options);\n }\n }\n\n showPlayerFallback() {\n this.el.classList.add('video-item-fallback-mode');\n this.el.dispatchEvent(createEvent('video-fall-back'));\n }\n\n videoCanPlay() {\n // Sometimes native video players reset the caption mode on play.\n // We reset it here to make sure there's no inconsistency with\n // the controls or expected value.\n if (this.jsPlayer) {\n this.jsPlayer.trigger('captionstatechange', {\n showCaptions: this.state.showCaptions,\n });\n }\n\n this.el.dispatchEvent(createEvent('video-can-play'));\n }\n\n videoReady() {\n this.el.dispatchEvent(createEvent('video-ready'));\n\n if (this.jsPlayer && this.jsPlayer.muted()) {\n this.jsPlayer.trigger('captionstatechange', { showCaptions: true });\n } else if (this.jsPlayer) {\n this.jsPlayer.trigger('captionstatechange', { showCaptions: false });\n }\n\n // This actually happens automatically because of the `autoplay` property\n // on the video element, but we call this to keep the button in sync\n if (this.state.autoplay) {\n this.playVideo();\n }\n }\n}\n"],"names":["VjsButton","CaptionToggle","constructor","player","options","super","this","updateTrackList","on","toggleDisplay","buildCSSClass","handleClick","toggleCaptions","textTrackList","remoteTextTracks","getVisibilityState","track","trackMode","i","length","kind","mode","captionState","newState","trigger","showCaptions","_","d","updateIcon","updateControlText_","removeClass","addClass","text","controlText","prototype","controlText_","registerComponent","Component","VjsBigPlayButton","createEl","props","innerHTML","className","el","call","type","createControlTextEl","VideoPlayer","state","getInitialState","playerType","getPlayerType","render","initializeVideo","initializeEventListeners","dataset","defaults","autoplay","captionLang","captionUrl","fullVideo","fallbackUrl","fallbackSrc","hasChrome","chrome","hlsUrl","src","id","inactivityTimeout","parseInt","lazyLoad","loop","muted","poster","showRemainingTime","spanishCaptionUrl","esCaptionUrl","controlsTimeout","playerStartTime","playerVolume","vttSeparator","containVideo","resetStates","videoHasLoaded","renderedTemplate","template","templateData","resizeVideoContainer","data","captionHTML","videoProperties","push","setup","Object","assign","join","windowHeight","window","innerHeight","innerWidth","videoWidth","style","maxWidth","checkVideo","document","createElement","canPlayType","updateCaptionSrc","jsPlayer","trackList","tracksToRemove","forEach","removeRemoteTextTrack","addRemoteTextTrack","srclang","label","addEventListener","setVideoSrc","srcData","updatedData","hls","loadSource","attachMedia","videoEl","VIDEOJS_NO_DYNAMIC_STYLE","querySelector","autoStartLoad","videoReady","supportedPlayer","controlBarComponents","getControlBarComponents","controls","preload","textTrackSettings","controlBar","children","html5","overrideNative","removeChild","addChild","ready","dispatchEvent","componentsInOrder","numCaptions","filter","Boolean","captionsPlugin","getPlayerProperty","propName","setPlayerProperty","arg","onPlayerEvent","eventName","callback","offPlayerEvent","off","removeEventListener","onePlayerEvent","one","args","once","e","duration","videoCanPlay","hideCaptions","videoItemFallback","playVideo","classList","add","isNotAlreadyPlaying","play","then","pause","visibilityState","pauseVideo","startLoad","stopLoad","tracks","idx","language","getPlayState","enableFades","playPromise","handleSuccessfulPlay","catch","error","console","log","showPlayerFallback","togglePlay"],"sourceRoot":""}