import { composeCustomComp, videojsComponent, videojsComponentButton, __MediaCMSComponent__, __MediaCMSButtonClickableComponent__, __SettingsPanelComponent__, __SettingsPanelInnerComponent__, __SettingsPanelTitleComponent__, __SettingsMenuComponent__, __SettingsMenuItemComponent__, __SettingsMenuItemLabelComponent__, __SettingsMenuItemContentComponent__ } from './components'; export function generateControlBarComponents(pluginInstanceRef) { function childrenGen( parentKey, child, allComps, parentsConn, level ){ var k, addedChild = false; allComps[level]= void 0 === allComps[level] ? [] : allComps[level]; for( k in child ){ if( child.hasOwnProperty(k) ){ if( child[k] && child[k].children ){ if( childrenGen( k, child[k].children, allComps, parentsConn, level + 1 ) ){ addedChild = true; allComps[level].push(k); parentsConn[k] = parentKey; } } else { addedChild = true; allComps[level].push(k); parentsConn[k] = parentKey; } } } return addedChild; } function gen(parent, ControlBar) { const componentsToAppend = [], parentsConnections = {}, appendedComponents = {}; let i, j, prnt, customCompKey, customCompName; if( parent.children ){ childrenGen( 'controlBar', parent.children, componentsToAppend, parentsConnections, 0 ); /*console.log( componentsToAppend ); console.log( parentsConnections );*/ i = 0; while(i' ).methods ) ); pluginInstanceRef.player.addChild( 'ActionsAnimations' ); } export function generateLoadingSpinnerComponent(pluginInstanceRef){ pluginInstanceRef.player.removeChild('LoadingSpinner'); videojs.registerComponent( 'LoadingSpinner', videojs.extend( __MediaCMSComponent__ , composeCustomComp( __MediaCMSComponent__, 'vjs-loading-spinner', '
\
\
\
\
\
\
\
' ).methods ) ); pluginInstanceRef.player.addChild( 'LoadingSpinner' ); } function initComponents(pluginInstanceRef, which, struct, args){ let k; let tmp; switch(which){ case 'bottomBackground': struct.bottomBackground = null; videojs.registerComponent("BottomBackground", videojs.extend( __MediaCMSComponent__ , composeCustomComp( __MediaCMSComponent__, 'vjs-bottom-bg' ).methods)); break; case 'progressControl': struct.progressControl = null; break; case '__settings': struct.settingsPanel = { children: { settingsPanelInner: { children: { settingsMenu: { children:{} }, }, }, }, }; tmp = composeCustomComp( __SettingsPanelComponent__, 'vjs-settings-root'); tmp.methods.constructor = function() { videojsComponent.apply(this, arguments); this.setAttribute('class', this.buildCSSClass()); const that = this; function onFocusout(ev){ if (that.el_.contains(ev.relatedTarget)) { return; } that.player_.trigger('focusoutSettingsPanel'); } pluginInstanceRef.on(this.player_, ['updatedSettingsPanelsVisibility'], function(){ videojs.dom[ this.state.isOpenSettingsOptions ? 'addClass' : 'removeClass' ]( that.el_, 'vjs-visible-panel' ); }); pluginInstanceRef.on(this.player_, ['openedSettingsPanel'], function( ev, openedFromKeyboard ){ that.el_.setAttribute('tabindex', '-1'); that.el_.addEventListener('focusout', onFocusout ); if( !!openedFromKeyboard ){ that.el_.querySelector('.vjs-settings-menu-item').focus(); } else{ that.el_.focus(); } }); pluginInstanceRef.on(this.player_, ['closedSettingsPanel'], function( ev, closedFromKeyboard ){ that.el_.removeAttribute('tabindex'); that.el_.removeEventListener('focusout', onFocusout ); if( !!closedFromKeyboard ){ that.el_.querySelector('.vjs-settings-menu-item').focus(); } }); }; videojs.registerComponent('SettingsPanel', videojs.extend( tmp.extend , tmp.methods)); videojs.registerComponent('SettingsPanelInner', videojs.extend( __SettingsPanelInnerComponent__, composeCustomComp( __SettingsPanelInnerComponent__ ).methods)); videojs.registerComponent('SettingsMenu', videojs.extend( __SettingsMenuComponent__, composeCustomComp( __SettingsMenuComponent__ ).methods)); if( args.enabledPlaybackSpeedPanel ){ struct.settingsPanel.children.settingsPanelInner.children.settingsMenu.children.selectedPlaybackSpeed = { children: { selectedPlaybackSpeedLabel: null, selectedPlaybackSpeedContent: null, } }; tmp = composeCustomComp( __SettingsMenuItemComponent__, 'vjs-selected-speed' ); tmp.methods.handleClick = function(ev){ this.player_.trigger('openPlaybackSpeedOptions', ! ev.screenX && ! ev.screenY ); }; videojs.registerComponent('SelectedPlaybackSpeed', videojs.extend( tmp.extend , tmp.methods)); videojs.registerComponent('SelectedPlaybackSpeedLabel', videojs.extend( __SettingsMenuItemLabelComponent__, composeCustomComp( __SettingsMenuItemLabelComponent__, null, 'Playback speed' ).methods)); tmp = composeCustomComp( __SettingsMenuItemContentComponent__, null, args.selectedPlaybackSpeed ); tmp.methods.constructor = function() { videojsComponent.apply(this, arguments); const that = this; that.el_.innerHTML = pluginInstanceRef.selectedPlaybackSpeedTitle(); this.setAttribute('class', this.buildCSSClass()); pluginInstanceRef.on(this.player_, ['updatedSelectedPlaybackSpeed'], function(){ that.el_.innerHTML = this.selectedPlaybackSpeedTitle(); }); }; videojs.registerComponent('SelectedPlaybackSpeedContent', videojs.extend( tmp.extend , tmp.methods)); } if( args.enabledResolutionsPanel ){ struct.settingsPanel.children.settingsPanelInner.children.settingsMenu.children.selectedResolution = { children: { selectedResolutionLabel: null, selectedResolutionContent: null, } }; tmp = composeCustomComp( __SettingsMenuItemComponent__, 'vjs-selected-quality' ); tmp.methods.handleClick = function(ev){ this.player_.trigger('openQualityOptions', ! ev.screenX && ! ev.screenY ); }; videojs.registerComponent('SelectedResolution', videojs.extend( tmp.extend , tmp.methods)); videojs.registerComponent('SelectedResolutionLabel', videojs.extend( __SettingsMenuItemLabelComponent__, composeCustomComp( __SettingsMenuItemLabelComponent__, null, 'Quality' ).methods)); tmp = composeCustomComp( __SettingsMenuItemContentComponent__, null, args.selectedResolution ); tmp.methods.constructor = function() { videojsComponent.apply(this, arguments); const that = this; that.el_.innerHTML = args.selectedResolution; this.setAttribute('class', this.buildCSSClass()); pluginInstanceRef.on(this.player_, ['updatedSelectedQuality'], function(){ that.el_.innerHTML = this.selectedQualityTitle(); }); }; videojs.registerComponent('SelectedResolutionContent', videojs.extend( tmp.extend , tmp.methods)); } break; case '__resolution': struct.resolutionsPanel = { children: { resolutionsPanelInner: { children: { resolutionsMenuTitle: { children: { resolutionsMenuBackButton: null } }, resolutionsMenu: { children: {} } } } } }; tmp = composeCustomComp( __SettingsPanelComponent__, 'vjs-resolutions-panel'); tmp.methods.constructor = function() { videojsComponent.apply(this, arguments); this.setAttribute('class', this.buildCSSClass()); const that = this; function onFocusout(ev){ if (that.el_.contains(ev.relatedTarget)) { return; } that.player_.trigger('focusoutResolutionsPanel'); } pluginInstanceRef.on(this.player_, ['updatedSettingsPanelsVisibility'], function(){ videojs.dom[ this.state.isOpenQualityOptions ? 'addClass' : 'removeClass' ]( that.el_, 'vjs-visible-panel' ); }); pluginInstanceRef.on(this.player_, ['openedQualities'], function(ev, openedFromKeyboard){ that.el_.setAttribute('tabindex', '-1'); that.el_.addEventListener('focusout', onFocusout); if( !!openedFromKeyboard ){ that.el_.querySelector('.vjs-setting-panel-title > *[role="button"]').focus(); } else{ that.el_.focus(); } }); pluginInstanceRef.on(this.player_, ['closedQualities'], function(ev, closedFromKeyboard){ that.el_.removeAttribute('tabindex'); that.el_.removeEventListener('focusout', onFocusout); if( !!closedFromKeyboard ){ that.el_.querySelector('.vjs-settings-menu-item').focus(); } }); }; videojs.registerComponent('ResolutionsPanel', videojs.extend( tmp.extend , tmp.methods)); videojs.registerComponent('ResolutionsPanelInner', videojs.extend( __SettingsPanelInnerComponent__, composeCustomComp( __SettingsPanelInnerComponent__ ).methods)); videojs.registerComponent('ResolutionsMenu', videojs.extend( __SettingsMenuComponent__, composeCustomComp( __SettingsMenuComponent__ ).methods)); videojs.registerComponent('ResolutionsMenuTitle', videojs.extend( __SettingsPanelTitleComponent__ , composeCustomComp( __SettingsPanelTitleComponent__, 'vjs-settings-back' ).methods)); tmp = composeCustomComp( __MediaCMSButtonClickableComponent__, null, 'Quality' ); tmp.methods.handleClick = function(ev){ this.player_.trigger('closeQualityOptions', ! ev.screenX && ! ev.screenY ); }; videojs.registerComponent('ResolutionsMenuBackButton', videojs.extend( tmp.extend , tmp.methods)); const resolutionKeys = (function(){ let i; const ret = []; const keys = Object.keys( args.resolutions ); const stringKeys = []; const numericKeys = []; i = 0; while( i < keys.length ){ if( isNaN( 0 + keys[i] ) ){ stringKeys.push( keys[i] ); } else{ numericKeys.push( [ parseFloat( keys[i] ), keys[i] ] ); } i += 1; } numericKeys.sort( (a, b) => b[0] - a[0] ); i = 0; while( i < numericKeys.length ){ ret.push( numericKeys[i][1] ); i += 1; } i = 0; while( i < stringKeys.length ){ ret.push( stringKeys[i] ); i += 1; } return ret; }()); let i = 0; while( i < resolutionKeys.length ){ k = resolutionKeys[i]; struct.resolutionsPanel.children.resolutionsPanelInner.children.resolutionsMenu.children[ 'resolutionOption_' + k ] = { children: { ['resolutionOption_' + k + '_content'] : null } }; (function( key, title ){ tmp = composeCustomComp( __SettingsMenuItemComponent__, key.toString() === pluginInstanceRef.state.theSelectedQuality.toString() ? 'vjs-selected-menu-item' : null, null/*, { 'data-opt': key }*/ ); tmp.methods.constructor = function(){ __SettingsMenuItemComponent__.apply(this, arguments); const that = this; this.qualityKey = key; this.setAttribute('data-opt', key); pluginInstanceRef.on(this.player_, ['updatedSelectedQuality'], function(){ videojs.dom[ that.qualityKey === this.state.theSelectedQuality ? 'addClass' : 'removeClass' ]( that.el_, 'vjs-selected-menu-item' ); }); }; tmp.methods.handleClick = function(){ this.player_.trigger('selectedQuality', this.el_.getAttribute('data-opt')); }; videojs.registerComponent('ResolutionOption_' + key, videojs.extend( tmp.extend , tmp.methods)); tmp = composeCustomComp( __SettingsMenuItemContentComponent__, null, title ); videojs.registerComponent('ResolutionOption_' + key + '_content', videojs.extend( tmp.extend , tmp.methods)); }( k, args.resolutions[k].title || k )); i += 1; } break; case '__playbackSpeed': struct.playbackSpeedsPanel = { children: { playbackSpeedsPanelInner: { children: { playbackSpeedsMenuTitle: { children: { playbackSpeedsMenuBackButton: null } }, playbackSpeedsMenu: { children: {} } } } } }; tmp = composeCustomComp( __SettingsPanelComponent__, 'vjs-playback-speed-panel'); tmp.methods.constructor = function() { videojsComponent.apply(this, arguments); this.setAttribute('class', this.buildCSSClass()); const that = this; function onFocusout(ev){ if (that.el_.contains(ev.relatedTarget)) { return; } that.player_.trigger('focusoutPlaybackSpeedsPanel'); } pluginInstanceRef.on(this.player_, ['updatedSettingsPanelsVisibility'], function(){ videojs.dom[ this.state.isOpenPlaybackSpeedOptions ? 'addClass' : 'removeClass' ]( that.el_, 'vjs-visible-panel' ); }); pluginInstanceRef.on(this.player_, ['openedPlaybackSpeeds'], function(ev, openedFromKeyboard){ that.el_.setAttribute('tabindex', '-1'); that.el_.addEventListener('focusout', onFocusout); if( !!openedFromKeyboard ){ that.el_.querySelector('.vjs-setting-panel-title > *[role="button"]').focus(); } else{ that.el_.focus(); } }); pluginInstanceRef.on(this.player_, ['closedPlaybackSpeeds'], function(ev, closedFromKeyboard){ that.el_.removeAttribute('tabindex'); that.el_.removeEventListener('focusout', onFocusout); if( !!closedFromKeyboard ){ that.el_.querySelector('.vjs-settings-menu-item').focus(); } }); }; videojs.registerComponent('PlaybackSpeedsPanel', videojs.extend( tmp.extend , tmp.methods)); videojs.registerComponent('PlaybackSpeedsPanelInner', videojs.extend( __SettingsPanelInnerComponent__, composeCustomComp( __SettingsPanelInnerComponent__ ).methods)); videojs.registerComponent('PlaybackSpeedsMenu', videojs.extend( __SettingsMenuComponent__, composeCustomComp( __SettingsMenuComponent__ ).methods)); videojs.registerComponent('PlaybackSpeedsMenuTitle', videojs.extend( __SettingsPanelTitleComponent__ , composeCustomComp( __SettingsPanelTitleComponent__, 'vjs-settings-back' ).methods)); tmp = composeCustomComp( __MediaCMSButtonClickableComponent__, null, 'Playback speed' ); tmp.methods.handleClick = function(ev){ this.player_.trigger('closePlaybackSpeedOptions', ! ev.screenX && ! ev.screenY ); }; videojs.registerComponent('PlaybackSpeedsMenuBackButton', videojs.extend( tmp.extend , tmp.methods)); for(k in args.playbackSpeeds){ if( args.playbackSpeeds.hasOwnProperty(k) ){ struct.playbackSpeedsPanel.children.playbackSpeedsPanelInner.children.playbackSpeedsMenu.children[ 'playbackSpeedOption_' + args.playbackSpeeds[k].speed ] = { children: { ['playbackSpeedOption_' + args.playbackSpeeds[k].speed + '_content'] : null } }; (function( key, title ){ tmp = composeCustomComp( __SettingsMenuItemComponent__, key.toString() === pluginInstanceRef.state.theSelectedPlaybackSpeed.toString() ? 'vjs-selected-menu-item' : null, null/*, { 'data-opt': key }*/ ); tmp.methods.constructor = function(){ __SettingsMenuItemComponent__.apply(this, arguments); const that = this; this.playbackSpeedKey = key; this.setAttribute('data-opt', key); pluginInstanceRef.on(this.player_, ['updatedSelectedPlaybackSpeed'], function(){ videojs.dom[ that.playbackSpeedKey === this.state.theSelectedPlaybackSpeed ? 'addClass' : 'removeClass' ]( that.el_, 'vjs-selected-menu-item' ); }); }; tmp.methods.handleClick = function(){ this.player_.trigger('selectedPlaybackSpeed', this.el_.getAttribute('data-opt')); }; videojs.registerComponent('PlaybackSpeedOption_' + key, videojs.extend( tmp.extend , tmp.methods)); tmp = composeCustomComp( __SettingsMenuItemContentComponent__, null, title ); videojs.registerComponent('PlaybackSpeedOption_' + key + '_content', videojs.extend( tmp.extend , tmp.methods)); }( args.playbackSpeeds[k].speed, args.playbackSpeeds[k].title || k )); } } break; case '__leftControls': struct.leftControls = { children: {} }; if( args.options.controlBar.previous ){ tmp = composeCustomComp( videojsComponentButton, 'vjs-previous-button' ); tmp.methods.handleClick = function(ev){ this.player_.trigger('clicked_previous_button'); }; videojs.registerComponent("PreviousButton", videojs.extend( tmp.extend , tmp.methods)); struct.leftControls.children.previousButton = null; } if( args.options.controlBar.play ){ struct.leftControls.children.playToggle = null; } if( args.options.controlBar.next ){ tmp = composeCustomComp( videojsComponentButton, 'vjs-next-button' ); tmp.methods.handleClick = function(ev){ this.player_.trigger('clicked_next_button'); }; videojs.registerComponent("NextButton", videojs.extend( tmp.extend , tmp.methods)); struct.leftControls.children.nextButton = null; } /*if( args.options.controlBar.previous ){ struct.leftControls.children.previous = null; } if( args.options.controlBar.next ){ // videojs.registerComponent("Next", videojs.extend( __MediaCMSComponent__ , composeCustomComp( __MediaCMSComponent__, 'vjs-bottom-bg' ).methods)); videojs.registerComponent("Next", videojs.extend( __MediaCMSComponent__ , composeCustomComp( __MediaCMSComponent__, 'vjs-bottom-bg' ).methods)); struct.leftControls.children.next = null; }*/ if( args.options.controlBar.volume ){ struct.leftControls.children.volumePanel = null; } if( args.options.controlBar.time ){ struct.leftControls.children.currentTimeDisplay = null; struct.leftControls.children.timeDivider = null; struct.leftControls.children.durationDisplay = null; } /*console.log( struct.leftControls.children );*/ videojs.registerComponent("LeftControls", videojs.extend( __MediaCMSComponent__ , composeCustomComp( __MediaCMSComponent__, 'vjs-left-controls' ).methods)); break; case '__rightControls': struct.rightControls = { children: {} }; if( args.enabledSettingsPanel ){ struct.rightControls.children.settingsToggle = null; } if( args.options.controlBar.theaterMode ){ struct.rightControls.children.theaterModeToggle = null; } if( args.options.controlBar.pictureInPicture ){ struct.rightControls.children.pictureInPictureToggle = null; } if( args.options.controlBar.fullscreen ){ struct.rightControls.children.fullscreenToggle = null; } videojs.registerComponent("RightControls", videojs.extend( __MediaCMSComponent__ , composeCustomComp( __MediaCMSComponent__, 'vjs-right-controls' ).methods)); if( args.enabledSettingsPanel ){ tmp = composeCustomComp( videojsComponentButton, 'vjs-settings-control vjs-icon-cog' ); tmp.methods.handleClick = function(ev){ this.player_.trigger( pluginInstanceRef.state.isOpenSettingsOptions ? 'closeSettingsPanel' : 'openSettingsPanel', ! ev.screenX && ! ev.screenY ); }; videojs.registerComponent("SettingsToggle", videojs.extend( tmp.extend , tmp.methods)); } if( args.options.controlBar.theaterMode ){ tmp = composeCustomComp( videojsComponentButton, 'vjs-theater-mode-control' ); tmp.methods.handleClick = function(){ this.player_.trigger('theatermodechange'); this.updateControlText(); }; tmp.methods.updateControlText = function(){ this.controlText(this.player_.localize(pluginInstanceRef.isTheaterMode() ? 'Default mode' : 'Theater mode')); }; videojs.registerComponent("TheaterModeToggle", videojs.extend( tmp.extend , tmp.methods)); } break; } } export function controlBarComponentsStructs( pluginInstanceRef, options ){ let struct = {}; const enabledResolutionsPanel = void 0 !== options.resolutions && void 0 !== options.resolutions.options && !!Object.keys( options.resolutions.options ).length; const enabledPlaybackSpeedPanel = void 0 !== options.playbackSpeeds && void 0 !== options.playbackSpeeds.options && !!Object.keys( options.playbackSpeeds.options ).length; const enabledSettingsPanel = enabledResolutionsPanel || enabledPlaybackSpeedPanel; // @note: At the moment the only setting option is video resolution. if( options.controlBar.bottomBackground ){ initComponents(pluginInstanceRef, 'bottomBackground', struct); } if( options.controlBar.progress ){ initComponents(pluginInstanceRef, 'progressControl', struct); } if( enabledResolutionsPanel ){ initComponents(pluginInstanceRef, '__resolution', struct, { resolutions: options.resolutions.options } ); } if( enabledPlaybackSpeedPanel ){ initComponents(pluginInstanceRef, '__playbackSpeed', struct, { playbackSpeeds: options.playbackSpeeds.options } ); } if( enabledSettingsPanel ){ if( enabledResolutionsPanel && enabledPlaybackSpeedPanel ){ initComponents(pluginInstanceRef, '__settings', struct, { enabledResolutionsPanel: enabledResolutionsPanel, selectedResolution: enabledResolutionsPanel ? options.resolutions.default : null, enabledPlaybackSpeedPanel: enabledPlaybackSpeedPanel, selectedPlaybackSpeed: enabledPlaybackSpeedPanel ? options.playbackSpeeds.default : null, }); } else if( enabledResolutionsPanel ){ initComponents(pluginInstanceRef, '__settings', struct, { enabledResolutionsPanel: enabledResolutionsPanel, selectedResolution: enabledResolutionsPanel ? options.resolutions.default : null, }); } else if( enabledPlaybackSpeedPanel ){ initComponents(pluginInstanceRef, '__settings', struct, { enabledPlaybackSpeedPanel: enabledPlaybackSpeedPanel, selectedPlaybackSpeed: enabledPlaybackSpeedPanel ? options.playbackSpeeds.default : null, }); } } if( options.controlBar.play || options.controlBar.previous || options.controlBar.next || options.controlBar.volume || options.controlBar.time ){ initComponents(pluginInstanceRef, '__leftControls', struct, { options: options } ); } if( enabledSettingsPanel || options.controlBar.theaterMode || options.controlBar.fullscreen || options.controlBar.pictureInPictureToggle ){ initComponents(pluginInstanceRef, '__rightControls', struct, { options: options, enabledSettingsPanel: enabledSettingsPanel } ); } return { children: struct }; }