diff options
Diffstat (limited to 'src/js/captions.js')
-rw-r--r-- | src/js/captions.js | 100 |
1 files changed, 49 insertions, 51 deletions
diff --git a/src/js/captions.js b/src/js/captions.js index bafcf87e..0506d1e6 100644 --- a/src/js/captions.js +++ b/src/js/captions.js @@ -6,7 +6,13 @@ import controls from './controls'; import i18n from './i18n'; import support from './support'; -import utils from './utils'; +import browser from './utils/browser'; +import { createElement, emptyElement, getAttributesFromSelector, insertAfter, removeElement, toggleClass } from './utils/elements'; +import { on, trigger } from './utils/events'; +import fetch from './utils/fetch'; +import is from './utils/is'; +import { getHTML } from './utils/strings'; +import { parseUrl } from './utils/urls'; const captions = { // Setup captions @@ -19,7 +25,7 @@ const captions = { // Only Vimeo and HTML5 video supported at this point if (!this.isVideo || this.isYouTube || (this.isHTML5 && !support.textTracks)) { // Clear menu and hide - if (utils.is.array(this.config.controls) && this.config.controls.includes('settings') && this.config.settings.includes('captions')) { + if (is.array(this.config.controls) && this.config.controls.includes('settings') && this.config.settings.includes('captions')) { controls.setCaptionsMenu.call(this); } @@ -27,15 +33,12 @@ const captions = { } // Inject the container - if (!utils.is.element(this.elements.captions)) { - this.elements.captions = utils.createElement('div', utils.getAttributesFromSelector(this.config.selectors.captions)); + if (!is.element(this.elements.captions)) { + this.elements.captions = createElement('div', getAttributesFromSelector(this.config.selectors.captions)); - utils.insertAfter(this.elements.captions, this.elements.wrapper); + insertAfter(this.elements.captions, this.elements.wrapper); } - // Get browser info - const browser = utils.getBrowser(); - // Fix IE captions if CORS is used // Fetch captions and inject as blobs instead (data URIs not supported!) if (browser.isIE && window.URL) { @@ -43,19 +46,18 @@ const captions = { Array.from(elements).forEach(track => { const src = track.getAttribute('src'); - const href = utils.parseUrl(src); + const url = parseUrl(src); - if (href.hostname !== window.location.href.hostname && [ + if (url !== null && url.hostname !== window.location.href.hostname && [ 'http:', 'https:', - ].includes(href.protocol)) { - utils - .fetch(src, 'blob') + ].includes(url.protocol)) { + fetch(src, 'blob') .then(blob => { track.setAttribute('src', window.URL.createObjectURL(blob)); }) .catch(() => { - utils.removeElement(track); + removeElement(track); }); } }); @@ -65,14 +67,14 @@ const captions = { let active = this.storage.get('captions'); // Otherwise fall back to the default config - if (!utils.is.boolean(active)) { + if (!is.boolean(active)) { ({ active } = this.config.captions); } // Get language from storage, fallback to config let language = this.storage.get('language') || this.config.captions.language; if (language === 'auto') { - [ language ] = (navigator.language || navigator.userLanguage).split('-'); + [language] = (navigator.language || navigator.userLanguage).split('-'); } // Set language and show if active captions.setLanguage.call(this, language, active); @@ -80,7 +82,7 @@ const captions = { // Watch changes to textTracks and update captions menu if (this.isHTML5) { const trackEvents = this.config.captions.update ? 'addtrack removetrack' : 'removetrack'; - utils.on(this.media.textTracks, trackEvents, captions.update.bind(this)); + on(this.media.textTracks, trackEvents, captions.update.bind(this)); } // Update available languages in list next tick (the event must not be triggered before the listeners) @@ -94,21 +96,19 @@ const captions = { // Handle tracks (add event listener and "pseudo"-default) if (this.isHTML5 && this.isVideo) { - tracks - .filter(track => !meta.get(track)) - .forEach(track => { - this.debug.log('Track added', track); - // Attempt to store if the original dom element was "default" - meta.set(track, { - default: track.mode === 'showing', - }); - - // Turn off native caption rendering to avoid double captions - track.mode = 'hidden'; - - // Add event listener for cue changes - utils.on(track, 'cuechange', () => captions.updateCues.call(this)); + tracks.filter(track => !meta.get(track)).forEach(track => { + this.debug.log('Track added', track); + // Attempt to store if the original dom element was "default" + meta.set(track, { + default: track.mode === 'showing', }); + + // Turn off native caption rendering to avoid double captions + track.mode = 'hidden'; + + // Add event listener for cue changes + on(track, 'cuechange', () => captions.updateCues.call(this)); + }); } const trackRemoved = !tracks.find(track => track === this.captions.currentTrackNode); @@ -120,7 +120,7 @@ const captions = { } // Enable or disable captions based on track length - utils.toggleClass(this.elements.container, this.config.classNames.captions.enabled, !utils.is.empty(tracks)); + toggleClass(this.elements.container, this.config.classNames.captions.enabled, !is.empty(tracks)); // Update available languages in list if ((this.config.controls || []).includes('settings') && this.config.settings.includes('captions')) { @@ -137,7 +137,7 @@ const captions = { return; } - if (!utils.is.number(index)) { + if (!is.number(index)) { this.debug.warn('Invalid caption argument', index); return; } @@ -166,7 +166,7 @@ const captions = { } // Trigger event - utils.dispatchEvent.call(this, this.media, 'languagechange'); + trigger.call(this, this.media, 'languagechange'); } if (this.isHTML5 && this.isVideo) { @@ -181,7 +181,7 @@ const captions = { }, setLanguage(language, show = true) { - if (!utils.is.string(language)) { + if (!is.string(language)) { this.debug.warn('Invalid language argument', language); return; } @@ -202,12 +202,10 @@ const captions = { const tracks = Array.from((this.media || {}).textTracks || []); // For HTML5, use cache instead of current tracks when it exists (if captions.update is false) // Filter out removed tracks and tracks that aren't captions/subtitles (for example metadata) - return tracks - .filter(track => !this.isHTML5 || update || this.captions.meta.has(track)) - .filter(track => [ - 'captions', - 'subtitles', - ].includes(track.kind)); + return tracks.filter(track => !this.isHTML5 || update || this.captions.meta.has(track)).filter(track => [ + 'captions', + 'subtitles', + ].includes(track.kind)); }, // Get the current track for the current language @@ -222,16 +220,16 @@ const captions = { getLabel(track) { let currentTrack = track; - if (!utils.is.track(currentTrack) && support.textTracks && this.captions.active) { + if (!is.track(currentTrack) && support.textTracks && this.captions.active) { currentTrack = captions.getCurrentTrack.call(this); } - if (utils.is.track(currentTrack)) { - if (!utils.is.empty(currentTrack.label)) { + if (is.track(currentTrack)) { + if (!is.empty(currentTrack.label)) { return currentTrack.label; } - if (!utils.is.empty(currentTrack.language)) { + if (!is.empty(currentTrack.language)) { return track.language.toUpperCase(); } @@ -249,13 +247,13 @@ const captions = { return; } - if (!utils.is.element(this.elements.captions)) { + if (!is.element(this.elements.captions)) { this.debug.warn('No captions element to render to'); return; } // Only accept array or empty input - if (!utils.is.nullOrUndefined(input) && !Array.isArray(input)) { + if (!is.nullOrUndefined(input) && !Array.isArray(input)) { this.debug.warn('updateCues: Invalid input', input); return; } @@ -267,7 +265,7 @@ const captions = { const track = captions.getCurrentTrack.call(this); cues = Array.from((track || {}).activeCues || []) .map(cue => cue.getCueAsHTML()) - .map(utils.getHTML); + .map(getHTML); } // Set new caption text @@ -276,13 +274,13 @@ const captions = { if (changed) { // Empty the container and create a new child element - utils.emptyElement(this.elements.captions); - const caption = utils.createElement('span', utils.getAttributesFromSelector(this.config.selectors.caption)); + emptyElement(this.elements.captions); + const caption = createElement('span', getAttributesFromSelector(this.config.selectors.caption)); caption.innerHTML = content; this.elements.captions.appendChild(caption); // Trigger event - utils.dispatchEvent.call(this, this.media, 'cuechange'); + trigger.call(this, this.media, 'cuechange'); } }, }; |