mirror of
https://github.com/videojs/video.js.git
synced 2025-02-18 12:24:02 +02:00
Improved JSDoc comments everywhere for new docs generation
closes #2270
This commit is contained in:
parent
f73f69c66c
commit
77a96bea6f
@ -56,6 +56,7 @@ CHANGELOG
|
|||||||
* @thijstriemstra added a logged error when a plugin is missing ([view](https://github.com/videojs/video.js/pull/1931))
|
* @thijstriemstra added a logged error when a plugin is missing ([view](https://github.com/videojs/video.js/pull/1931))
|
||||||
* @gkatsev fixed the texttrackchange event and text track display for non-native tracks ([view](https://github.com/videojs/video.js/pull/2215))
|
* @gkatsev fixed the texttrackchange event and text track display for non-native tracks ([view](https://github.com/videojs/video.js/pull/2215))
|
||||||
* @mischizzle fixed event.relatedTarget in Firefox ([view](https://github.com/videojs/video.js/pull/2025))
|
* @mischizzle fixed event.relatedTarget in Firefox ([view](https://github.com/videojs/video.js/pull/2025))
|
||||||
|
* @mboles updated JSDoc comments everywhere to prepare for new docs ([view](https://github.com/videojs/video.js/pull/2270))
|
||||||
|
|
||||||
--------------------
|
--------------------
|
||||||
|
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
/**
|
/**
|
||||||
* This code injects the required base styles in the head of the document.
|
* @file base-styles.js
|
||||||
*/
|
*
|
||||||
|
* This code injects the required base styles in the head of the document.
|
||||||
|
*/
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
|
|
||||||
|
@ -1,22 +1,39 @@
|
|||||||
|
/**
|
||||||
|
* @file big-play-button.js
|
||||||
|
*/
|
||||||
import Button from './button.js';
|
import Button from './button.js';
|
||||||
import Component from './component.js';
|
import Component from './component.js';
|
||||||
|
|
||||||
/* Big Play Button
|
|
||||||
================================================================================ */
|
|
||||||
/**
|
/**
|
||||||
* Initial play button. Shows before the video has played. The hiding of the
|
* Initial play button. Shows before the video has played. The hiding of the
|
||||||
* big play button is done via CSS and player states.
|
* big play button is done via CSS and player states.
|
||||||
* @param {Player|Object} player
|
*
|
||||||
* @param {Object=} options
|
* @param {Object} player Main Player
|
||||||
* @class
|
* @param {Object=} options Object of option names and values
|
||||||
* @constructor
|
* @extends Button
|
||||||
|
* @class BigPlayButton
|
||||||
*/
|
*/
|
||||||
class BigPlayButton extends Button {
|
class BigPlayButton extends Button {
|
||||||
|
|
||||||
|
constructor(player, options) {
|
||||||
|
super(player, options);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return 'vjs-big-play-button';
|
return 'vjs-big-play-button';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handles click for play
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
this.player_.play();
|
this.player_.play();
|
||||||
}
|
}
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file button.js
|
||||||
|
*/
|
||||||
import Component from './component';
|
import Component from './component';
|
||||||
import * as Dom from './utils/dom.js';
|
import * as Dom from './utils/dom.js';
|
||||||
import * as Events from './utils/events.js';
|
import * as Events from './utils/events.js';
|
||||||
@ -5,12 +8,11 @@ import * as Fn from './utils/fn.js';
|
|||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
import assign from 'object.assign';
|
import assign from 'object.assign';
|
||||||
|
|
||||||
/* Button - Base class for all buttons
|
|
||||||
================================================================================ */
|
|
||||||
/**
|
/**
|
||||||
* Base class for all buttons
|
* Base class for all buttons
|
||||||
* @param {Player|Object} player
|
*
|
||||||
* @param {Object=} options
|
* @param {Object} player Main Player
|
||||||
|
* @param {Object=} options Object of option names and values
|
||||||
* @extends Component
|
* @extends Component
|
||||||
* @class Button
|
* @class Button
|
||||||
*/
|
*/
|
||||||
@ -27,6 +29,14 @@ class Button extends Component {
|
|||||||
this.on('blur', this.handleBlur);
|
this.on('blur', this.handleBlur);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @param {String=} type Element's node type. e.g. 'div'
|
||||||
|
* @param {Object=} props An object of element attributes that should be set on the element Tag name
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl(type='button', props={}) {
|
createEl(type='button', props={}) {
|
||||||
// Add standard Aria and Tabindex info
|
// Add standard Aria and Tabindex info
|
||||||
props = assign({
|
props = assign({
|
||||||
@ -49,6 +59,13 @@ class Button extends Component {
|
|||||||
return el;
|
return el;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Controls text - both request and localize
|
||||||
|
*
|
||||||
|
* @param {String} text Text for button
|
||||||
|
* @return {String}
|
||||||
|
* @method controlText
|
||||||
|
*/
|
||||||
controlText(text) {
|
controlText(text) {
|
||||||
if (!text) return this.controlText_ || 'Need Text';
|
if (!text) return this.controlText_ || 'Need Text';
|
||||||
|
|
||||||
@ -58,19 +75,37 @@ class Button extends Component {
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allows sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String}
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-control vjs-button ${super.buildCSSClass()}`;
|
return `vjs-control vjs-button ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Click - Override with specific functionality for button
|
/**
|
||||||
|
* Handle Click - Override with specific functionality for button
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {}
|
handleClick() {}
|
||||||
|
|
||||||
// Focus - Add keyboard functionality to element
|
/**
|
||||||
|
* Handle Focus - Add keyboard functionality to element
|
||||||
|
*
|
||||||
|
* @method handleFocus
|
||||||
|
*/
|
||||||
handleFocus() {
|
handleFocus() {
|
||||||
Events.on(document, 'keydown', Fn.bind(this, this.handleKeyPress));
|
Events.on(document, 'keydown', Fn.bind(this, this.handleKeyPress));
|
||||||
}
|
}
|
||||||
|
|
||||||
// KeyPress (document level) - Trigger click when keys are pressed
|
/**
|
||||||
|
* Handle KeyPress (document level) - Trigger click when keys are pressed
|
||||||
|
*
|
||||||
|
* @method handleKeyPress
|
||||||
|
*/
|
||||||
handleKeyPress(event) {
|
handleKeyPress(event) {
|
||||||
// Check for space bar (32) or enter (13) keys
|
// Check for space bar (32) or enter (13) keys
|
||||||
if (event.which === 32 || event.which === 13) {
|
if (event.which === 32 || event.which === 13) {
|
||||||
@ -79,7 +114,11 @@ class Button extends Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Blur - Remove keyboard triggers
|
/**
|
||||||
|
* Handle Blur - Remove keyboard triggers
|
||||||
|
*
|
||||||
|
* @method handleBlur
|
||||||
|
*/
|
||||||
handleBlur() {
|
handleBlur() {
|
||||||
Events.off(document, 'keydown', Fn.bind(this, this.handleKeyPress));
|
Events.off(document, 'keydown', Fn.bind(this, this.handleKeyPress));
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
/**
|
/**
|
||||||
* @fileoverview Player Component - Base class for all UI objects
|
* @file component.js
|
||||||
*
|
*
|
||||||
|
* Player Component - Base class for all UI objects
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
@ -16,31 +17,31 @@ import mergeOptions from './utils/merge-options.js';
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Base UI Component class
|
* Base UI Component class
|
||||||
*
|
|
||||||
* Components are embeddable UI objects that are represented by both a
|
* Components are embeddable UI objects that are represented by both a
|
||||||
* javascript object and an element in the DOM. They can be children of other
|
* javascript object and an element in the DOM. They can be children of other
|
||||||
* components, and can have many children themselves.
|
* components, and can have many children themselves.
|
||||||
*
|
* ```js
|
||||||
* // adding a button to the player
|
* // adding a button to the player
|
||||||
* var button = player.addChild('button');
|
* var button = player.addChild('button');
|
||||||
* button.el(); // -> button element
|
* button.el(); // -> button element
|
||||||
*
|
* ```
|
||||||
|
* ```html
|
||||||
* <div class="video-js">
|
* <div class="video-js">
|
||||||
* <div class="vjs-button">Button</div>
|
* <div class="vjs-button">Button</div>
|
||||||
* </div>
|
* </div>
|
||||||
*
|
* ```
|
||||||
* Components are also event emitters.
|
* Components are also event emitters.
|
||||||
*
|
* ```js
|
||||||
* button.on('click', function(){
|
* button.on('click', function(){
|
||||||
* console.log('Button Clicked!');
|
* console.log('Button Clicked!');
|
||||||
* });
|
* });
|
||||||
*
|
|
||||||
* button.trigger('customevent');
|
* button.trigger('customevent');
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {Object} player Main Player
|
* @param {Object} player Main Player
|
||||||
* @param {Object=} options
|
* @param {Object=} options Object of option names and values
|
||||||
* @class
|
* @param {Function=} ready Ready callback function
|
||||||
* @constructor
|
* @class Component
|
||||||
*/
|
*/
|
||||||
class Component {
|
class Component {
|
||||||
|
|
||||||
@ -105,6 +106,8 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Dispose of the component and all child components
|
* Dispose of the component and all child components
|
||||||
|
*
|
||||||
|
* @method dispose
|
||||||
*/
|
*/
|
||||||
dispose() {
|
dispose() {
|
||||||
this.trigger({ type: 'dispose', bubbles: false });
|
this.trigger({ type: 'dispose', bubbles: false });
|
||||||
@ -139,6 +142,7 @@ class Component {
|
|||||||
* Return the component's player
|
* Return the component's player
|
||||||
*
|
*
|
||||||
* @return {Player}
|
* @return {Player}
|
||||||
|
* @method player
|
||||||
*/
|
*/
|
||||||
player() {
|
player() {
|
||||||
return this.player_;
|
return this.player_;
|
||||||
@ -146,14 +150,12 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Deep merge of options objects
|
* Deep merge of options objects
|
||||||
*
|
|
||||||
* Whenever a property is an object on both options objects
|
* Whenever a property is an object on both options objects
|
||||||
* the two properties will be merged using mergeOptions.
|
* the two properties will be merged using mergeOptions.
|
||||||
*
|
|
||||||
* This is used for merging options for child components. We
|
* This is used for merging options for child components. We
|
||||||
* want it to be easy to override individual options on a child
|
* want it to be easy to override individual options on a child
|
||||||
* component without having to rewrite all the other default options.
|
* component without having to rewrite all the other default options.
|
||||||
*
|
* ```js
|
||||||
* Parent.prototype.options_ = {
|
* Parent.prototype.options_ = {
|
||||||
* children: {
|
* children: {
|
||||||
* 'childOne': { 'foo': 'bar', 'asdf': 'fdsa' },
|
* 'childOne': { 'foo': 'bar', 'asdf': 'fdsa' },
|
||||||
@ -170,9 +172,9 @@ class Component {
|
|||||||
* }
|
* }
|
||||||
*
|
*
|
||||||
* this.options(newOptions);
|
* this.options(newOptions);
|
||||||
*
|
* ```
|
||||||
* RESULT
|
* RESULT
|
||||||
*
|
* ```js
|
||||||
* {
|
* {
|
||||||
* children: {
|
* children: {
|
||||||
* 'childOne': { 'foo': 'baz', 'asdf': 'fdsa', 'abc': '123' },
|
* 'childOne': { 'foo': 'baz', 'asdf': 'fdsa', 'abc': '123' },
|
||||||
@ -181,9 +183,11 @@ class Component {
|
|||||||
* 'childFour': {}
|
* 'childFour': {}
|
||||||
* }
|
* }
|
||||||
* }
|
* }
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {Object} obj Object of new option values
|
* @param {Object} obj Object of new option values
|
||||||
* @return {Object} A NEW object of this.options_ and obj merged
|
* @return {Object} A NEW object of this.options_ and obj merged
|
||||||
|
* @method options
|
||||||
*/
|
*/
|
||||||
options(obj) {
|
options(obj) {
|
||||||
log.warn('this.options() has been deprecated and will be moved to the constructor in 6.0');
|
log.warn('this.options() has been deprecated and will be moved to the constructor in 6.0');
|
||||||
@ -198,10 +202,12 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the component's DOM element
|
* Get the component's DOM element
|
||||||
*
|
* ```js
|
||||||
* var domEl = myComponent.el();
|
* var domEl = myComponent.el();
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @return {Element}
|
* @return {Element}
|
||||||
|
* @method el
|
||||||
*/
|
*/
|
||||||
el() {
|
el() {
|
||||||
return this.el_;
|
return this.el_;
|
||||||
@ -213,6 +219,7 @@ class Component {
|
|||||||
* @param {String=} tagName Element's node type. e.g. 'div'
|
* @param {String=} tagName Element's node type. e.g. 'div'
|
||||||
* @param {Object=} attributes An object of element attributes that should be set on the element
|
* @param {Object=} attributes An object of element attributes that should be set on the element
|
||||||
* @return {Element}
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
*/
|
*/
|
||||||
createEl(tagName, attributes) {
|
createEl(tagName, attributes) {
|
||||||
return Dom.createEl(tagName, attributes);
|
return Dom.createEl(tagName, attributes);
|
||||||
@ -247,6 +254,7 @@ class Component {
|
|||||||
* Will either be the same as el() or a new element defined in createEl().
|
* Will either be the same as el() or a new element defined in createEl().
|
||||||
*
|
*
|
||||||
* @return {Element}
|
* @return {Element}
|
||||||
|
* @method contentEl
|
||||||
*/
|
*/
|
||||||
contentEl() {
|
contentEl() {
|
||||||
return this.contentEl_ || this.el_;
|
return this.contentEl_ || this.el_;
|
||||||
@ -254,10 +262,12 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the component's ID
|
* Get the component's ID
|
||||||
*
|
* ```js
|
||||||
* var id = myComponent.id();
|
* var id = myComponent.id();
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @return {String}
|
* @return {String}
|
||||||
|
* @method id
|
||||||
*/
|
*/
|
||||||
id() {
|
id() {
|
||||||
return this.id_;
|
return this.id_;
|
||||||
@ -265,10 +275,12 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the component's name. The name is often used to reference the component.
|
* Get the component's name. The name is often used to reference the component.
|
||||||
*
|
* ```js
|
||||||
* var name = myComponent.name();
|
* var name = myComponent.name();
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @return {String}
|
* @return {String}
|
||||||
|
* @method name
|
||||||
*/
|
*/
|
||||||
name() {
|
name() {
|
||||||
return this.name_;
|
return this.name_;
|
||||||
@ -276,10 +288,12 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get an array of all child components
|
* Get an array of all child components
|
||||||
*
|
* ```js
|
||||||
* var kids = myComponent.children();
|
* var kids = myComponent.children();
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @return {Array} The children
|
* @return {Array} The children
|
||||||
|
* @method children
|
||||||
*/
|
*/
|
||||||
children() {
|
children() {
|
||||||
return this.children_;
|
return this.children_;
|
||||||
@ -289,6 +303,7 @@ class Component {
|
|||||||
* Returns a child component with the provided ID
|
* Returns a child component with the provided ID
|
||||||
*
|
*
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method getChildById
|
||||||
*/
|
*/
|
||||||
getChildById(id) {
|
getChildById(id) {
|
||||||
return this.childIndex_[id];
|
return this.childIndex_[id];
|
||||||
@ -298,6 +313,7 @@ class Component {
|
|||||||
* Returns a child component with the provided name
|
* Returns a child component with the provided name
|
||||||
*
|
*
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method getChild
|
||||||
*/
|
*/
|
||||||
getChild(name) {
|
getChild(name) {
|
||||||
return this.childNameIndex_[name];
|
return this.childNameIndex_[name];
|
||||||
@ -305,7 +321,7 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds a child component inside this component
|
* Adds a child component inside this component
|
||||||
*
|
* ```js
|
||||||
* myComponent.el();
|
* myComponent.el();
|
||||||
* // -> <div class='my-component'></div>
|
* // -> <div class='my-component'></div>
|
||||||
* myComponent.children();
|
* myComponent.children();
|
||||||
@ -314,9 +330,9 @@ class Component {
|
|||||||
* var myButton = myComponent.addChild('MyButton');
|
* var myButton = myComponent.addChild('MyButton');
|
||||||
* // -> <div class='my-component'><div class="my-button">myButton<div></div>
|
* // -> <div class='my-component'><div class="my-button">myButton<div></div>
|
||||||
* // -> myButton === myComonent.children()[0];
|
* // -> myButton === myComonent.children()[0];
|
||||||
*
|
* ```
|
||||||
* Pass in options for child constructors and options for children of the child
|
* Pass in options for child constructors and options for children of the child
|
||||||
*
|
* ```js
|
||||||
* var myButton = myComponent.addChild('MyButton', {
|
* var myButton = myComponent.addChild('MyButton', {
|
||||||
* text: 'Press Me',
|
* text: 'Press Me',
|
||||||
* children: {
|
* children: {
|
||||||
@ -325,11 +341,12 @@ class Component {
|
|||||||
* }
|
* }
|
||||||
* }
|
* }
|
||||||
* });
|
* });
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {String|Component} child The class name or instance of a child to add
|
* @param {String|Component} child The class name or instance of a child to add
|
||||||
* @param {Object=} options Options, including options to be passed to children of the child.
|
* @param {Object=} options Options, including options to be passed to children of the child.
|
||||||
* @return {Component} The child component (created by this process if a string was used)
|
* @return {Component} The child component (created by this process if a string was used)
|
||||||
* @suppress {accessControls|checkRegExp|checkTypes|checkVars|const|constantProperty|deprecated|duplicate|es5Strict|fileoverviewTags|globalThis|invalidCasts|missingProperties|nonStandardJsDocs|strictModuleDepCheck|undefinedNames|undefinedVars|unknownDefines|uselessCode|visibility}
|
* @method addChild
|
||||||
*/
|
*/
|
||||||
addChild(child, options={}) {
|
addChild(child, options={}) {
|
||||||
let component;
|
let component;
|
||||||
@ -397,6 +414,7 @@ class Component {
|
|||||||
* child component's element from this component's element
|
* child component's element from this component's element
|
||||||
*
|
*
|
||||||
* @param {Component} component Component to remove
|
* @param {Component} component Component to remove
|
||||||
|
* @method removeChild
|
||||||
*/
|
*/
|
||||||
removeChild(component) {
|
removeChild(component) {
|
||||||
if (typeof component === 'string') {
|
if (typeof component === 'string') {
|
||||||
@ -433,7 +451,7 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Add and initialize default child components from options
|
* Add and initialize default child components from options
|
||||||
*
|
* ```js
|
||||||
* // when an instance of MyComponent is created, all children in options
|
* // when an instance of MyComponent is created, all children in options
|
||||||
* // will be added to the instance by their name strings and options
|
* // will be added to the instance by their name strings and options
|
||||||
* MyComponent.prototype.options_.children = {
|
* MyComponent.prototype.options_.children = {
|
||||||
@ -441,8 +459,9 @@ class Component {
|
|||||||
* myChildOption: true
|
* myChildOption: true
|
||||||
* }
|
* }
|
||||||
* }
|
* }
|
||||||
*
|
* ```
|
||||||
* // Or when creating the component
|
* // Or when creating the component
|
||||||
|
* ```js
|
||||||
* var myComp = new MyComponent(player, {
|
* var myComp = new MyComponent(player, {
|
||||||
* children: {
|
* children: {
|
||||||
* myChildComponent: {
|
* myChildComponent: {
|
||||||
@ -450,10 +469,10 @@ class Component {
|
|||||||
* }
|
* }
|
||||||
* }
|
* }
|
||||||
* });
|
* });
|
||||||
*
|
* ```
|
||||||
* The children option can also be an Array of child names or
|
* The children option can also be an Array of child names or
|
||||||
* child options objects (that also include a 'name' key).
|
* child options objects (that also include a 'name' key).
|
||||||
*
|
* ```js
|
||||||
* var myComp = new MyComponent(player, {
|
* var myComp = new MyComponent(player, {
|
||||||
* children: [
|
* children: [
|
||||||
* 'button',
|
* 'button',
|
||||||
@ -463,7 +482,9 @@ class Component {
|
|||||||
* }
|
* }
|
||||||
* ]
|
* ]
|
||||||
* });
|
* });
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
|
* @method initChildren
|
||||||
*/
|
*/
|
||||||
initChildren() {
|
initChildren() {
|
||||||
let children = this.options_.children;
|
let children = this.options_.children;
|
||||||
@ -528,6 +549,7 @@ class Component {
|
|||||||
* Allows sub components to stack CSS class names
|
* Allows sub components to stack CSS class names
|
||||||
*
|
*
|
||||||
* @return {String} The constructed class name
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
*/
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
// Child classes can include a function that does:
|
// Child classes can include a function that does:
|
||||||
@ -537,26 +559,24 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Add an event listener to this component's element
|
* Add an event listener to this component's element
|
||||||
*
|
* ```js
|
||||||
* var myFunc = function(){
|
* var myFunc = function(){
|
||||||
* var myComponent = this;
|
* var myComponent = this;
|
||||||
* // Do something when the event is fired
|
* // Do something when the event is fired
|
||||||
* };
|
* };
|
||||||
*
|
*
|
||||||
* myComponent.on('eventType', myFunc);
|
* myComponent.on('eventType', myFunc);
|
||||||
*
|
* ```
|
||||||
* The context of myFunc will be myComponent unless previously bound.
|
* The context of myFunc will be myComponent unless previously bound.
|
||||||
*
|
|
||||||
* Alternatively, you can add a listener to another element or component.
|
* Alternatively, you can add a listener to another element or component.
|
||||||
*
|
* ```js
|
||||||
* myComponent.on(otherElement, 'eventName', myFunc);
|
* myComponent.on(otherElement, 'eventName', myFunc);
|
||||||
* myComponent.on(otherComponent, 'eventName', myFunc);
|
* myComponent.on(otherComponent, 'eventName', myFunc);
|
||||||
*
|
* ```
|
||||||
* The benefit of using this over `VjsEvents.on(otherElement, 'eventName', myFunc)`
|
* The benefit of using this over `VjsEvents.on(otherElement, 'eventName', myFunc)`
|
||||||
* and `otherComponent.on('eventName', myFunc)` is that this way the listeners
|
* and `otherComponent.on('eventName', myFunc)` is that this way the listeners
|
||||||
* will be automatically cleaned up when either component is disposed.
|
* will be automatically cleaned up when either component is disposed.
|
||||||
* It will also bind myComponent as the context of myFunc.
|
* It will also bind myComponent as the context of myFunc.
|
||||||
*
|
|
||||||
* **NOTE**: When using this on elements in the page other than window
|
* **NOTE**: When using this on elements in the page other than window
|
||||||
* and document (both permanent), if you remove the element from the DOM
|
* and document (both permanent), if you remove the element from the DOM
|
||||||
* you need to call `myComponent.trigger(el, 'dispose')` on it to clean up
|
* you need to call `myComponent.trigger(el, 'dispose')` on it to clean up
|
||||||
@ -565,7 +585,8 @@ class Component {
|
|||||||
* @param {String|Component} first The event type or other component
|
* @param {String|Component} first The event type or other component
|
||||||
* @param {Function|String} second The event handler or event type
|
* @param {Function|String} second The event handler or event type
|
||||||
* @param {Function} third The event handler
|
* @param {Function} third The event handler
|
||||||
* @return {Component} self
|
* @return {Component}
|
||||||
|
* @method on
|
||||||
*/
|
*/
|
||||||
on(first, second, third) {
|
on(first, second, third) {
|
||||||
if (typeof first === 'string' || Array.isArray(first)) {
|
if (typeof first === 'string' || Array.isArray(first)) {
|
||||||
@ -613,23 +634,24 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Remove an event listener from this component's element
|
* Remove an event listener from this component's element
|
||||||
*
|
* ```js
|
||||||
* myComponent.off('eventType', myFunc);
|
* myComponent.off('eventType', myFunc);
|
||||||
*
|
* ```
|
||||||
* If myFunc is excluded, ALL listeners for the event type will be removed.
|
* If myFunc is excluded, ALL listeners for the event type will be removed.
|
||||||
* If eventType is excluded, ALL listeners will be removed from the component.
|
* If eventType is excluded, ALL listeners will be removed from the component.
|
||||||
*
|
|
||||||
* Alternatively you can use `off` to remove listeners that were added to other
|
* Alternatively you can use `off` to remove listeners that were added to other
|
||||||
* elements or components using `myComponent.on(otherComponent...`.
|
* elements or components using `myComponent.on(otherComponent...`.
|
||||||
* In this case both the event type and listener function are REQUIRED.
|
* In this case both the event type and listener function are REQUIRED.
|
||||||
*
|
* ```js
|
||||||
* myComponent.off(otherElement, 'eventType', myFunc);
|
* myComponent.off(otherElement, 'eventType', myFunc);
|
||||||
* myComponent.off(otherComponent, 'eventType', myFunc);
|
* myComponent.off(otherComponent, 'eventType', myFunc);
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {String=|Component} first The event type or other component
|
* @param {String=|Component} first The event type or other component
|
||||||
* @param {Function=|String} second The listener function or event type
|
* @param {Function=|String} second The listener function or event type
|
||||||
* @param {Function=} third The listener for other component
|
* @param {Function=} third The listener for other component
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method off
|
||||||
*/
|
*/
|
||||||
off(first, second, third) {
|
off(first, second, third) {
|
||||||
if (!first || typeof first === 'string' || Array.isArray(first)) {
|
if (!first || typeof first === 'string' || Array.isArray(first)) {
|
||||||
@ -660,19 +682,21 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Add an event listener to be triggered only once and then removed
|
* Add an event listener to be triggered only once and then removed
|
||||||
*
|
* ```js
|
||||||
* myComponent.one('eventName', myFunc);
|
* myComponent.one('eventName', myFunc);
|
||||||
*
|
* ```
|
||||||
* Alternatively you can add a listener to another element or component
|
* Alternatively you can add a listener to another element or component
|
||||||
* that will be triggered only once.
|
* that will be triggered only once.
|
||||||
*
|
* ```js
|
||||||
* myComponent.one(otherElement, 'eventName', myFunc);
|
* myComponent.one(otherElement, 'eventName', myFunc);
|
||||||
* myComponent.one(otherComponent, 'eventName', myFunc);
|
* myComponent.one(otherComponent, 'eventName', myFunc);
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {String|Component} first The event type or other component
|
* @param {String|Component} first The event type or other component
|
||||||
* @param {Function|String} second The listener function or event type
|
* @param {Function|String} second The listener function or event type
|
||||||
* @param {Function=} third The listener function for other component
|
* @param {Function=} third The listener function for other component
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method one
|
||||||
*/
|
*/
|
||||||
one(first, second, third) {
|
one(first, second, third) {
|
||||||
if (typeof first === 'string' || Array.isArray(first)) {
|
if (typeof first === 'string' || Array.isArray(first)) {
|
||||||
@ -698,15 +722,17 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Trigger an event on an element
|
* Trigger an event on an element
|
||||||
*
|
* ```js
|
||||||
* myComponent.trigger('eventName');
|
* myComponent.trigger('eventName');
|
||||||
* myComponent.trigger({'type':'eventName'});
|
* myComponent.trigger({'type':'eventName'});
|
||||||
* myComponent.trigger('eventName', {data: 'some data'});
|
* myComponent.trigger('eventName', {data: 'some data'});
|
||||||
* myComponent.trigger({'type':'eventName'}, {data: 'some data'});
|
* myComponent.trigger({'type':'eventName'}, {data: 'some data'});
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {Event|Object|String} event A string (the type) or an event object with a type attribute
|
* @param {Event|Object|String} event A string (the type) or an event object with a type attribute
|
||||||
* @param {Object} [hash] data hash to pass along with the event
|
* @param {Object} [hash] data hash to pass along with the event
|
||||||
* @return {Component} self
|
* @return {Component} self
|
||||||
|
* @method trigger
|
||||||
*/
|
*/
|
||||||
trigger(event, hash) {
|
trigger(event, hash) {
|
||||||
Events.trigger(this.el_, event, hash);
|
Events.trigger(this.el_, event, hash);
|
||||||
@ -714,13 +740,13 @@ class Component {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Bind a listener to the component's ready state
|
* Bind a listener to the component's ready state.
|
||||||
*
|
|
||||||
* Different from event listeners in that if the ready event has already happened
|
* Different from event listeners in that if the ready event has already happened
|
||||||
* it will trigger the function immediately.
|
* it will trigger the function immediately.
|
||||||
*
|
*
|
||||||
* @param {Function} fn Ready listener
|
* @param {Function} fn Ready listener
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method ready
|
||||||
*/
|
*/
|
||||||
ready(fn) {
|
ready(fn) {
|
||||||
if (fn) {
|
if (fn) {
|
||||||
@ -739,6 +765,7 @@ class Component {
|
|||||||
* Trigger the ready listeners
|
* Trigger the ready listeners
|
||||||
*
|
*
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method triggerReady
|
||||||
*/
|
*/
|
||||||
triggerReady() {
|
triggerReady() {
|
||||||
this.isReady_ = true;
|
this.isReady_ = true;
|
||||||
@ -766,6 +793,7 @@ class Component {
|
|||||||
*
|
*
|
||||||
* @param {String} classToCheck Classname to check
|
* @param {String} classToCheck Classname to check
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method hasClass
|
||||||
*/
|
*/
|
||||||
hasClass(classToCheck) {
|
hasClass(classToCheck) {
|
||||||
return Dom.hasElClass(this.el_, classToCheck);
|
return Dom.hasElClass(this.el_, classToCheck);
|
||||||
@ -776,6 +804,7 @@ class Component {
|
|||||||
*
|
*
|
||||||
* @param {String} classToAdd Classname to add
|
* @param {String} classToAdd Classname to add
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method addClass
|
||||||
*/
|
*/
|
||||||
addClass(classToAdd) {
|
addClass(classToAdd) {
|
||||||
Dom.addElClass(this.el_, classToAdd);
|
Dom.addElClass(this.el_, classToAdd);
|
||||||
@ -783,10 +812,11 @@ class Component {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Remove a CSS class name from the component's element
|
* Remove and return a CSS class name from the component's element
|
||||||
*
|
*
|
||||||
* @param {String} classToRemove Classname to remove
|
* @param {String} classToRemove Classname to remove
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method removeClass
|
||||||
*/
|
*/
|
||||||
removeClass(classToRemove) {
|
removeClass(classToRemove) {
|
||||||
Dom.removeElClass(this.el_, classToRemove);
|
Dom.removeElClass(this.el_, classToRemove);
|
||||||
@ -797,6 +827,7 @@ class Component {
|
|||||||
* Show the component element if hidden
|
* Show the component element if hidden
|
||||||
*
|
*
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method show
|
||||||
*/
|
*/
|
||||||
show() {
|
show() {
|
||||||
this.removeClass('vjs-hidden');
|
this.removeClass('vjs-hidden');
|
||||||
@ -807,6 +838,7 @@ class Component {
|
|||||||
* Hide the component element if currently showing
|
* Hide the component element if currently showing
|
||||||
*
|
*
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
|
* @method hide
|
||||||
*/
|
*/
|
||||||
hide() {
|
hide() {
|
||||||
this.addClass('vjs-hidden');
|
this.addClass('vjs-hidden');
|
||||||
@ -819,6 +851,7 @@ class Component {
|
|||||||
*
|
*
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
* @private
|
* @private
|
||||||
|
* @method lockShowing
|
||||||
*/
|
*/
|
||||||
lockShowing() {
|
lockShowing() {
|
||||||
this.addClass('vjs-lock-showing');
|
this.addClass('vjs-lock-showing');
|
||||||
@ -831,6 +864,7 @@ class Component {
|
|||||||
*
|
*
|
||||||
* @return {Component}
|
* @return {Component}
|
||||||
* @private
|
* @private
|
||||||
|
* @method unlockShowing
|
||||||
*/
|
*/
|
||||||
unlockShowing() {
|
unlockShowing() {
|
||||||
this.removeClass('vjs-lock-showing');
|
this.removeClass('vjs-lock-showing');
|
||||||
@ -839,7 +873,6 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Set or get the width of the component (CSS values)
|
* Set or get the width of the component (CSS values)
|
||||||
*
|
|
||||||
* Setting the video tag dimension values only works with values in pixels.
|
* Setting the video tag dimension values only works with values in pixels.
|
||||||
* Percent values will not work.
|
* Percent values will not work.
|
||||||
* Some percents can be used, but width()/height() will return the number + %,
|
* Some percents can be used, but width()/height() will return the number + %,
|
||||||
@ -849,6 +882,7 @@ class Component {
|
|||||||
* @param {Boolean} skipListeners Skip the 'resize' event trigger
|
* @param {Boolean} skipListeners Skip the 'resize' event trigger
|
||||||
* @return {Component} This component, when setting the width
|
* @return {Component} This component, when setting the width
|
||||||
* @return {Number|String} The width, when getting
|
* @return {Number|String} The width, when getting
|
||||||
|
* @method width
|
||||||
*/
|
*/
|
||||||
width(num, skipListeners) {
|
width(num, skipListeners) {
|
||||||
return this.dimension('width', num, skipListeners);
|
return this.dimension('width', num, skipListeners);
|
||||||
@ -856,7 +890,6 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get or set the height of the component (CSS values)
|
* Get or set the height of the component (CSS values)
|
||||||
*
|
|
||||||
* Setting the video tag dimension values only works with values in pixels.
|
* Setting the video tag dimension values only works with values in pixels.
|
||||||
* Percent values will not work.
|
* Percent values will not work.
|
||||||
* Some percents can be used, but width()/height() will return the number + %,
|
* Some percents can be used, but width()/height() will return the number + %,
|
||||||
@ -866,6 +899,7 @@ class Component {
|
|||||||
* @param {Boolean=} skipListeners Skip the resize event trigger
|
* @param {Boolean=} skipListeners Skip the resize event trigger
|
||||||
* @return {Component} This component, when setting the height
|
* @return {Component} This component, when setting the height
|
||||||
* @return {Number|String} The height, when getting
|
* @return {Number|String} The height, when getting
|
||||||
|
* @method height
|
||||||
*/
|
*/
|
||||||
height(num, skipListeners) {
|
height(num, skipListeners) {
|
||||||
return this.dimension('height', num, skipListeners);
|
return this.dimension('height', num, skipListeners);
|
||||||
@ -874,9 +908,10 @@ class Component {
|
|||||||
/**
|
/**
|
||||||
* Set both width and height at the same time
|
* Set both width and height at the same time
|
||||||
*
|
*
|
||||||
* @param {Number|String} width
|
* @param {Number|String} width Width of player
|
||||||
* @param {Number|String} height
|
* @param {Number|String} height Height of player
|
||||||
* @return {Component} The component
|
* @return {Component} The component
|
||||||
|
* @method dimensions
|
||||||
*/
|
*/
|
||||||
dimensions(width, height) {
|
dimensions(width, height) {
|
||||||
// Skip resize listeners on width for optimization
|
// Skip resize listeners on width for optimization
|
||||||
@ -885,10 +920,8 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get or set width or height
|
* Get or set width or height
|
||||||
*
|
|
||||||
* This is the shared code for the width() and height() methods.
|
* This is the shared code for the width() and height() methods.
|
||||||
* All for an integer, integer + 'px' or integer + '%';
|
* All for an integer, integer + 'px' or integer + '%';
|
||||||
*
|
|
||||||
* Known issue: Hidden elements officially have a width of 0. We're defaulting
|
* Known issue: Hidden elements officially have a width of 0. We're defaulting
|
||||||
* to the style.width value and falling back to computedStyle which has the
|
* to the style.width value and falling back to computedStyle which has the
|
||||||
* hidden element issue. Info, but probably not an efficient fix:
|
* hidden element issue. Info, but probably not an efficient fix:
|
||||||
@ -900,6 +933,7 @@ class Component {
|
|||||||
* @return {Component} The component if a dimension was set
|
* @return {Component} The component if a dimension was set
|
||||||
* @return {Number|String} The dimension if nothing was set
|
* @return {Number|String} The dimension if nothing was set
|
||||||
* @private
|
* @private
|
||||||
|
* @method dimension
|
||||||
*/
|
*/
|
||||||
dimension(widthOrHeight, num, skipListeners) {
|
dimension(widthOrHeight, num, skipListeners) {
|
||||||
if (num !== undefined) {
|
if (num !== undefined) {
|
||||||
@ -949,13 +983,13 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Emit 'tap' events when touch events are supported
|
* Emit 'tap' events when touch events are supported
|
||||||
*
|
|
||||||
* This is used to support toggling the controls through a tap on the video.
|
* This is used to support toggling the controls through a tap on the video.
|
||||||
*
|
|
||||||
* We're requiring them to be enabled because otherwise every component would
|
* We're requiring them to be enabled because otherwise every component would
|
||||||
* have this extra overhead unnecessarily, on mobile devices where extra
|
* have this extra overhead unnecessarily, on mobile devices where extra
|
||||||
* overhead is especially bad.
|
* overhead is especially bad.
|
||||||
|
*
|
||||||
* @private
|
* @private
|
||||||
|
* @method emitTapEvents
|
||||||
*/
|
*/
|
||||||
emitTapEvents() {
|
emitTapEvents() {
|
||||||
// Track the start time so we can determine how long the touch lasted
|
// Track the start time so we can determine how long the touch lasted
|
||||||
@ -992,7 +1026,7 @@ class Component {
|
|||||||
// So, if we moved only a small distance, this could still be a tap
|
// So, if we moved only a small distance, this could still be a tap
|
||||||
const xdiff = event.touches[0].pageX - firstTouch.pageX;
|
const xdiff = event.touches[0].pageX - firstTouch.pageX;
|
||||||
const ydiff = event.touches[0].pageY - firstTouch.pageY;
|
const ydiff = event.touches[0].pageY - firstTouch.pageY;
|
||||||
const touchDistance = Math.sqrt(xdiff * xdiff + ydiff * ydiff);
|
const touchDistance = Math.sqrt(xdiff * xdiff + ydiff * ydiff);
|
||||||
|
|
||||||
if (touchDistance > tapMovementThreshold) {
|
if (touchDistance > tapMovementThreshold) {
|
||||||
couldBeTap = false;
|
couldBeTap = false;
|
||||||
@ -1032,12 +1066,10 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Report user touch activity when touch events occur
|
* Report user touch activity when touch events occur
|
||||||
*
|
|
||||||
* User activity is used to determine when controls should show/hide. It's
|
* User activity is used to determine when controls should show/hide. It's
|
||||||
* relatively simple when it comes to mouse events, because any mouse event
|
* relatively simple when it comes to mouse events, because any mouse event
|
||||||
* should show the controls. So we capture mouse events that bubble up to the
|
* should show the controls. So we capture mouse events that bubble up to the
|
||||||
* player and report activity when that happens.
|
* player and report activity when that happens.
|
||||||
*
|
|
||||||
* With touch events it isn't as easy. We can't rely on touch events at the
|
* With touch events it isn't as easy. We can't rely on touch events at the
|
||||||
* player level, because a tap (touchstart + touchend) on the video itself on
|
* player level, because a tap (touchstart + touchend) on the video itself on
|
||||||
* mobile devices is meant to turn controls off (and on). User activity is
|
* mobile devices is meant to turn controls off (and on). User activity is
|
||||||
@ -1045,13 +1077,13 @@ class Component {
|
|||||||
* turns the controls off, then the touchend event bubbles up to the player,
|
* turns the controls off, then the touchend event bubbles up to the player,
|
||||||
* which if it reported user activity, would turn the controls right back on.
|
* which if it reported user activity, would turn the controls right back on.
|
||||||
* (We also don't want to completely block touch events from bubbling up)
|
* (We also don't want to completely block touch events from bubbling up)
|
||||||
*
|
|
||||||
* Also a touchmove, touch+hold, and anything other than a tap is not supposed
|
* Also a touchmove, touch+hold, and anything other than a tap is not supposed
|
||||||
* to turn the controls back on on a mobile device.
|
* to turn the controls back on on a mobile device.
|
||||||
*
|
|
||||||
* Here we're setting the default component behavior to report user activity
|
* Here we're setting the default component behavior to report user activity
|
||||||
* whenever touch events happen, and this can be turned off by components that
|
* whenever touch events happen, and this can be turned off by components that
|
||||||
* want touch events to act differently.
|
* want touch events to act differently.
|
||||||
|
*
|
||||||
|
* @method enableTouchActivity
|
||||||
*/
|
*/
|
||||||
enableTouchActivity() {
|
enableTouchActivity() {
|
||||||
// Don't continue if the root player doesn't support reporting user activity
|
// Don't continue if the root player doesn't support reporting user activity
|
||||||
@ -1087,9 +1119,11 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Creates timeout and sets up disposal automatically.
|
* Creates timeout and sets up disposal automatically.
|
||||||
|
*
|
||||||
* @param {Function} fn The function to run after the timeout.
|
* @param {Function} fn The function to run after the timeout.
|
||||||
* @param {Number} timeout Number of ms to delay before executing specified function.
|
* @param {Number} timeout Number of ms to delay before executing specified function.
|
||||||
* @return {Number} Returns the timeout ID
|
* @return {Number} Returns the timeout ID
|
||||||
|
* @method setTimeout
|
||||||
*/
|
*/
|
||||||
setTimeout(fn, timeout) {
|
setTimeout(fn, timeout) {
|
||||||
fn = Fn.bind(this, fn);
|
fn = Fn.bind(this, fn);
|
||||||
@ -1110,8 +1144,10 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Clears a timeout and removes the associated dispose listener
|
* Clears a timeout and removes the associated dispose listener
|
||||||
|
*
|
||||||
* @param {Number} timeoutId The id of the timeout to clear
|
* @param {Number} timeoutId The id of the timeout to clear
|
||||||
* @return {Number} Returns the timeout ID
|
* @return {Number} Returns the timeout ID
|
||||||
|
* @method clearTimeout
|
||||||
*/
|
*/
|
||||||
clearTimeout(timeoutId) {
|
clearTimeout(timeoutId) {
|
||||||
window.clearTimeout(timeoutId);
|
window.clearTimeout(timeoutId);
|
||||||
@ -1127,9 +1163,11 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Creates an interval and sets up disposal automatically.
|
* Creates an interval and sets up disposal automatically.
|
||||||
|
*
|
||||||
* @param {Function} fn The function to run every N seconds.
|
* @param {Function} fn The function to run every N seconds.
|
||||||
* @param {Number} interval Number of ms to delay before executing specified function.
|
* @param {Number} interval Number of ms to delay before executing specified function.
|
||||||
* @return {Number} Returns the interval ID
|
* @return {Number} Returns the interval ID
|
||||||
|
* @method setInterval
|
||||||
*/
|
*/
|
||||||
setInterval(fn, interval) {
|
setInterval(fn, interval) {
|
||||||
fn = Fn.bind(this, fn);
|
fn = Fn.bind(this, fn);
|
||||||
@ -1149,8 +1187,10 @@ class Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Clears an interval and removes the associated dispose listener
|
* Clears an interval and removes the associated dispose listener
|
||||||
|
*
|
||||||
* @param {Number} intervalId The id of the interval to clear
|
* @param {Number} intervalId The id of the interval to clear
|
||||||
* @return {Number} Returns the interval ID
|
* @return {Number} Returns the interval ID
|
||||||
|
* @method clearInterval
|
||||||
*/
|
*/
|
||||||
clearInterval(intervalId) {
|
clearInterval(intervalId) {
|
||||||
window.clearInterval(intervalId);
|
window.clearInterval(intervalId);
|
||||||
@ -1164,6 +1204,14 @@ class Component {
|
|||||||
return intervalId;
|
return intervalId;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Registers a component
|
||||||
|
*
|
||||||
|
* @param {String} name Name of the component to register
|
||||||
|
* @param {Object} comp The component to register
|
||||||
|
* @static
|
||||||
|
* @method registerComponent
|
||||||
|
*/
|
||||||
static registerComponent(name, comp) {
|
static registerComponent(name, comp) {
|
||||||
if (!Component.components_) {
|
if (!Component.components_) {
|
||||||
Component.components_ = {};
|
Component.components_ = {};
|
||||||
@ -1173,6 +1221,14 @@ class Component {
|
|||||||
return comp;
|
return comp;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets a component by name
|
||||||
|
*
|
||||||
|
* @param {String} name Name of the component to get
|
||||||
|
* @return {Component}
|
||||||
|
* @static
|
||||||
|
* @method getComponent
|
||||||
|
*/
|
||||||
static getComponent(name) {
|
static getComponent(name) {
|
||||||
if (Component.components_ && Component.components_[name]) {
|
if (Component.components_ && Component.components_[name]) {
|
||||||
return Component.components_[name];
|
return Component.components_[name];
|
||||||
@ -1184,6 +1240,14 @@ class Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Sets up the constructor using the supplied init method
|
||||||
|
* or uses the init of the parent object
|
||||||
|
*
|
||||||
|
* @param {Object} props An object of properties
|
||||||
|
* @static
|
||||||
|
* @method extend
|
||||||
|
*/
|
||||||
static extend(props) {
|
static extend(props) {
|
||||||
props = props || {};
|
props = props || {};
|
||||||
// Set up the constructor using the supplied init method
|
// Set up the constructor using the supplied init method
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file control-bar.js
|
||||||
|
*/
|
||||||
import Component from '../component.js';
|
import Component from '../component.js';
|
||||||
|
|
||||||
// Required children
|
// Required children
|
||||||
@ -20,13 +23,18 @@ import CustomControlSpacer from './spacer-controls/custom-control-spacer.js';
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Container of main controls
|
* Container of main controls
|
||||||
* @param {Player|Object} player
|
*
|
||||||
* @param {Object=} options
|
|
||||||
* @class
|
|
||||||
* @constructor
|
|
||||||
* @extends Component
|
* @extends Component
|
||||||
|
* @class ControlBar
|
||||||
*/
|
*/
|
||||||
class ControlBar extends Component {
|
class ControlBar extends Component {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-control-bar'
|
className: 'vjs-control-bar'
|
||||||
|
@ -1,19 +1,32 @@
|
|||||||
|
/**
|
||||||
|
* @file fullscreen-toggle.js
|
||||||
|
*/
|
||||||
import Button from '../button.js';
|
import Button from '../button.js';
|
||||||
import Component from '../component.js';
|
import Component from '../component.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Toggle fullscreen video
|
* Toggle fullscreen video
|
||||||
* @param {Player|Object} player
|
*
|
||||||
* @param {Object=} options
|
* @extends Button
|
||||||
* @class
|
* @class FullscreenToggle
|
||||||
* @extends vjs.Button
|
|
||||||
*/
|
*/
|
||||||
class FullscreenToggle extends Button {
|
class FullscreenToggle extends Button {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-fullscreen-control ${super.buildCSSClass()}`;
|
return `vjs-fullscreen-control ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handles click for full screen
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
if (!this.player_.isFullscreen()) {
|
if (!this.player_.isFullscreen()) {
|
||||||
this.player_.requestFullscreen();
|
this.player_.requestFullscreen();
|
||||||
|
@ -1,15 +1,24 @@
|
|||||||
|
/**
|
||||||
|
* @file live-display.js
|
||||||
|
*/
|
||||||
import Component from '../component';
|
import Component from '../component';
|
||||||
import * as Dom from '../utils/dom.js';
|
import * as Dom from '../utils/dom.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Displays the live indicator
|
* Displays the live indicator
|
||||||
* TODO - Future make it click to snap to live
|
* TODO - Future make it click to snap to live
|
||||||
* @param {Player|Object} player
|
*
|
||||||
* @param {Object=} options
|
* @extends Component
|
||||||
* @constructor
|
* @class LiveDisplay
|
||||||
*/
|
*/
|
||||||
class LiveDisplay extends Component {
|
class LiveDisplay extends Component {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
var el = super.createEl('div', {
|
var el = super.createEl('div', {
|
||||||
className: 'vjs-live-control vjs-control'
|
className: 'vjs-live-control vjs-control'
|
||||||
|
@ -1,13 +1,17 @@
|
|||||||
|
/**
|
||||||
|
* @file mute-toggle.js
|
||||||
|
*/
|
||||||
import Button from '../button';
|
import Button from '../button';
|
||||||
import Component from '../component';
|
import Component from '../component';
|
||||||
import * as Dom from '../utils/dom.js';
|
import * as Dom from '../utils/dom.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A button component for muting the audio
|
* A button component for muting the audio
|
||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Button
|
||||||
|
* @class MuteToggle
|
||||||
*/
|
*/
|
||||||
class MuteToggle extends Button {
|
class MuteToggle extends Button {
|
||||||
|
|
||||||
@ -30,14 +34,30 @@ class MuteToggle extends Button {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-mute-control ${super.buildCSSClass()}`;
|
return `vjs-mute-control ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle click on mute
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
this.player_.muted( this.player_.muted() ? false : true );
|
this.player_.muted( this.player_.muted() ? false : true );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update volume
|
||||||
|
*
|
||||||
|
* @method update
|
||||||
|
*/
|
||||||
update() {
|
update() {
|
||||||
var vol = this.player_.volume(),
|
var vol = this.player_.volume(),
|
||||||
level = 3;
|
level = 3;
|
||||||
|
@ -1,12 +1,16 @@
|
|||||||
|
/**
|
||||||
|
* @file play-toggle.js
|
||||||
|
*/
|
||||||
import Button from '../button.js';
|
import Button from '../button.js';
|
||||||
import Component from '../component.js';
|
import Component from '../component.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Button to toggle between play and pause
|
* Button to toggle between play and pause
|
||||||
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @class
|
* @extends Button
|
||||||
* @constructor
|
* @class PlayToggle
|
||||||
*/
|
*/
|
||||||
class PlayToggle extends Button {
|
class PlayToggle extends Button {
|
||||||
|
|
||||||
@ -17,11 +21,21 @@ class PlayToggle extends Button {
|
|||||||
this.on(player, 'pause', this.handlePause);
|
this.on(player, 'pause', this.handlePause);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-play-control ${super.buildCSSClass()}`;
|
return `vjs-play-control ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
// handleClick - Toggle between play and pause
|
/**
|
||||||
|
* Handle click to toggle between play and pause
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
if (this.player_.paused()) {
|
if (this.player_.paused()) {
|
||||||
this.player_.play();
|
this.player_.play();
|
||||||
@ -30,14 +44,22 @@ class PlayToggle extends Button {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// handlePlay - Add the vjs-playing class to the element so it can change appearance
|
/**
|
||||||
|
* Add the vjs-playing class to the element so it can change appearance
|
||||||
|
*
|
||||||
|
* @method handlePlay
|
||||||
|
*/
|
||||||
handlePlay() {
|
handlePlay() {
|
||||||
this.removeClass('vjs-paused');
|
this.removeClass('vjs-paused');
|
||||||
this.addClass('vjs-playing');
|
this.addClass('vjs-playing');
|
||||||
this.controlText('Pause'); // change the button text to "Pause"
|
this.controlText('Pause'); // change the button text to "Pause"
|
||||||
}
|
}
|
||||||
|
|
||||||
// handlePause - Add the vjs-paused class to the element so it can change appearance
|
/**
|
||||||
|
* Add the vjs-paused class to the element so it can change appearance
|
||||||
|
*
|
||||||
|
* @method handlePause
|
||||||
|
*/
|
||||||
handlePause() {
|
handlePause() {
|
||||||
this.removeClass('vjs-playing');
|
this.removeClass('vjs-playing');
|
||||||
this.addClass('vjs-paused');
|
this.addClass('vjs-paused');
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file playback-rate-menu-button.js
|
||||||
|
*/
|
||||||
import MenuButton from '../../menu/menu-button.js';
|
import MenuButton from '../../menu/menu-button.js';
|
||||||
import Menu from '../../menu/menu.js';
|
import Menu from '../../menu/menu.js';
|
||||||
import PlaybackRateMenuItem from './playback-rate-menu-item.js';
|
import PlaybackRateMenuItem from './playback-rate-menu-item.js';
|
||||||
@ -9,7 +12,8 @@ import * as Dom from '../../utils/dom.js';
|
|||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends MenuButton
|
||||||
|
* @class PlaybackRateMenuButton
|
||||||
*/
|
*/
|
||||||
class PlaybackRateMenuButton extends MenuButton {
|
class PlaybackRateMenuButton extends MenuButton {
|
||||||
|
|
||||||
@ -23,6 +27,12 @@ class PlaybackRateMenuButton extends MenuButton {
|
|||||||
this.on(player, 'ratechange', this.updateLabel);
|
this.on(player, 'ratechange', this.updateLabel);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
let el = super.createEl();
|
let el = super.createEl();
|
||||||
|
|
||||||
@ -36,11 +46,22 @@ class PlaybackRateMenuButton extends MenuButton {
|
|||||||
return el;
|
return el;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-playback-rate ${super.buildCSSClass()}`;
|
return `vjs-playback-rate ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Menu creation
|
/**
|
||||||
|
* Create the playback rate menu
|
||||||
|
*
|
||||||
|
* @return {Menu} Menu object populated with items
|
||||||
|
* @method createMenu
|
||||||
|
*/
|
||||||
createMenu() {
|
createMenu() {
|
||||||
let menu = new Menu(this.player());
|
let menu = new Menu(this.player());
|
||||||
let rates = this.playbackRates();
|
let rates = this.playbackRates();
|
||||||
@ -56,11 +77,21 @@ class PlaybackRateMenuButton extends MenuButton {
|
|||||||
return menu;
|
return menu;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Updates ARIA accessibility attributes
|
||||||
|
*
|
||||||
|
* @method updateARIAAttributes
|
||||||
|
*/
|
||||||
updateARIAAttributes() {
|
updateARIAAttributes() {
|
||||||
// Current playback rate
|
// Current playback rate
|
||||||
this.el().setAttribute('aria-valuenow', this.player().playbackRate());
|
this.el().setAttribute('aria-valuenow', this.player().playbackRate());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle menu item click
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
// select next rate option
|
// select next rate option
|
||||||
let currentRate = this.player().playbackRate();
|
let currentRate = this.player().playbackRate();
|
||||||
@ -77,10 +108,22 @@ class PlaybackRateMenuButton extends MenuButton {
|
|||||||
this.player().playbackRate(newRate);
|
this.player().playbackRate(newRate);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get possible playback rates
|
||||||
|
*
|
||||||
|
* @return {Array} Possible playback rates
|
||||||
|
* @method playbackRates
|
||||||
|
*/
|
||||||
playbackRates() {
|
playbackRates() {
|
||||||
return this.options_['playbackRates'] || (this.options_.playerOptions && this.options_.playerOptions['playbackRates']);
|
return this.options_['playbackRates'] || (this.options_.playerOptions && this.options_.playerOptions['playbackRates']);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get supported playback rates
|
||||||
|
*
|
||||||
|
* @return {Array} Supported playback rates
|
||||||
|
* @method playbackRateSupported
|
||||||
|
*/
|
||||||
playbackRateSupported() {
|
playbackRateSupported() {
|
||||||
return this.player().tech
|
return this.player().tech
|
||||||
&& this.player().tech['featuresPlaybackRate']
|
&& this.player().tech['featuresPlaybackRate']
|
||||||
@ -91,6 +134,8 @@ class PlaybackRateMenuButton extends MenuButton {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Hide playback rate controls when they're no playback rate options to select
|
* Hide playback rate controls when they're no playback rate options to select
|
||||||
|
*
|
||||||
|
* @method updateVisibility
|
||||||
*/
|
*/
|
||||||
updateVisibility() {
|
updateVisibility() {
|
||||||
if (this.playbackRateSupported()) {
|
if (this.playbackRateSupported()) {
|
||||||
@ -102,6 +147,8 @@ class PlaybackRateMenuButton extends MenuButton {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Update button label when rate changed
|
* Update button label when rate changed
|
||||||
|
*
|
||||||
|
* @method updateLabel
|
||||||
*/
|
*/
|
||||||
updateLabel() {
|
updateLabel() {
|
||||||
if (this.playbackRateSupported()) {
|
if (this.playbackRateSupported()) {
|
||||||
|
@ -1,10 +1,16 @@
|
|||||||
|
/**
|
||||||
|
* @file playback-rate-menu-item.js
|
||||||
|
*/
|
||||||
import MenuItem from '../../menu/menu-item.js';
|
import MenuItem from '../../menu/menu-item.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The specific menu item type for selecting a playback rate
|
* The specific menu item type for selecting a playback rate
|
||||||
*
|
*
|
||||||
* @constructor
|
* @param {Player|Object} player
|
||||||
|
* @param {Object=} options
|
||||||
|
* @extends MenuItem
|
||||||
|
* @class PlaybackRateMenuItem
|
||||||
*/
|
*/
|
||||||
class PlaybackRateMenuItem extends MenuItem {
|
class PlaybackRateMenuItem extends MenuItem {
|
||||||
|
|
||||||
@ -23,11 +29,21 @@ class PlaybackRateMenuItem extends MenuItem {
|
|||||||
this.on(player, 'ratechange', this.update);
|
this.on(player, 'ratechange', this.update);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle click on menu item
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
super.handleClick();
|
super.handleClick();
|
||||||
this.player().playbackRate(this.rate);
|
this.player().playbackRate(this.rate);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update playback rate with selected rate
|
||||||
|
*
|
||||||
|
* @method update
|
||||||
|
*/
|
||||||
update() {
|
update() {
|
||||||
this.selected(this.player().playbackRate() === this.rate);
|
this.selected(this.player().playbackRate() === this.rate);
|
||||||
}
|
}
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file load-progress-bar.js
|
||||||
|
*/
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import * as Dom from '../../utils/dom.js';
|
import * as Dom from '../../utils/dom.js';
|
||||||
|
|
||||||
@ -6,7 +9,8 @@ import * as Dom from '../../utils/dom.js';
|
|||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Component
|
||||||
|
* @class LoadProgressBar
|
||||||
*/
|
*/
|
||||||
class LoadProgressBar extends Component {
|
class LoadProgressBar extends Component {
|
||||||
|
|
||||||
@ -15,6 +19,12 @@ class LoadProgressBar extends Component {
|
|||||||
this.on(player, 'progress', this.update);
|
this.on(player, 'progress', this.update);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-load-progress',
|
className: 'vjs-load-progress',
|
||||||
@ -22,6 +32,11 @@ class LoadProgressBar extends Component {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update progress bar
|
||||||
|
*
|
||||||
|
* @method update
|
||||||
|
*/
|
||||||
update() {
|
update() {
|
||||||
let buffered = this.player_.buffered();
|
let buffered = this.player_.buffered();
|
||||||
let duration = this.player_.duration();
|
let duration = this.player_.duration();
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file play-progress-bar.js
|
||||||
|
*/
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -5,10 +8,17 @@ import Component from '../../component.js';
|
|||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Component
|
||||||
|
* @class PlayProgressBar
|
||||||
*/
|
*/
|
||||||
class PlayProgressBar extends Component {
|
class PlayProgressBar extends Component {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-play-progress',
|
className: 'vjs-play-progress',
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file progress-control.js
|
||||||
|
*/
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import SeekBar from './seek-bar.js';
|
import SeekBar from './seek-bar.js';
|
||||||
|
|
||||||
@ -7,9 +10,17 @@ import SeekBar from './seek-bar.js';
|
|||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Component
|
||||||
|
* @class ProgressControl
|
||||||
*/
|
*/
|
||||||
class ProgressControl extends Component {
|
class ProgressControl extends Component {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-progress-control vjs-control'
|
className: 'vjs-progress-control vjs-control'
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file seek-bar.js
|
||||||
|
*/
|
||||||
import Slider from '../../slider/slider.js';
|
import Slider from '../../slider/slider.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import LoadProgressBar from './load-progress-bar.js';
|
import LoadProgressBar from './load-progress-bar.js';
|
||||||
@ -11,7 +14,8 @@ import roundFloat from '../../utils/round-float.js';
|
|||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Slider
|
||||||
|
* @class SeekBar
|
||||||
*/
|
*/
|
||||||
class SeekBar extends Slider {
|
class SeekBar extends Slider {
|
||||||
|
|
||||||
@ -21,6 +25,12 @@ class SeekBar extends Slider {
|
|||||||
player.ready(Fn.bind(this, this.updateARIAAttributes));
|
player.ready(Fn.bind(this, this.updateARIAAttributes));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-progress-holder',
|
className: 'vjs-progress-holder',
|
||||||
@ -28,6 +38,11 @@ class SeekBar extends Slider {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update ARIA accessibility attributes
|
||||||
|
*
|
||||||
|
* @method updateARIAAttributes
|
||||||
|
*/
|
||||||
updateARIAAttributes() {
|
updateARIAAttributes() {
|
||||||
// Allows for smooth scrubbing, when player can't keep up.
|
// Allows for smooth scrubbing, when player can't keep up.
|
||||||
let time = (this.player_.scrubbing()) ? this.player_.getCache().currentTime : this.player_.currentTime();
|
let time = (this.player_.scrubbing()) ? this.player_.getCache().currentTime : this.player_.currentTime();
|
||||||
@ -35,11 +50,22 @@ class SeekBar extends Slider {
|
|||||||
this.el_.setAttribute('aria-valuetext', formatTime(time, this.player_.duration())); // human readable value of progress bar (time complete)
|
this.el_.setAttribute('aria-valuetext', formatTime(time, this.player_.duration())); // human readable value of progress bar (time complete)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get percentage of video played
|
||||||
|
*
|
||||||
|
* @return {Number} Percentage played
|
||||||
|
* @method getPercent
|
||||||
|
*/
|
||||||
getPercent() {
|
getPercent() {
|
||||||
let percent = this.player_.currentTime() / this.player_.duration();
|
let percent = this.player_.currentTime() / this.player_.duration();
|
||||||
return percent >= 1 ? 1 : percent;
|
return percent >= 1 ? 1 : percent;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle mouse down on seek bar
|
||||||
|
*
|
||||||
|
* @method handleMouseDown
|
||||||
|
*/
|
||||||
handleMouseDown(event) {
|
handleMouseDown(event) {
|
||||||
super.handleMouseDown(event);
|
super.handleMouseDown(event);
|
||||||
|
|
||||||
@ -49,6 +75,11 @@ class SeekBar extends Slider {
|
|||||||
this.player_.pause();
|
this.player_.pause();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle mouse move on seek bar
|
||||||
|
*
|
||||||
|
* @method handleMouseMove
|
||||||
|
*/
|
||||||
handleMouseMove(event) {
|
handleMouseMove(event) {
|
||||||
let newTime = this.calculateDistance(event) * this.player_.duration();
|
let newTime = this.calculateDistance(event) * this.player_.duration();
|
||||||
|
|
||||||
@ -59,6 +90,11 @@ class SeekBar extends Slider {
|
|||||||
this.player_.currentTime(newTime);
|
this.player_.currentTime(newTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle mouse up on seek bar
|
||||||
|
*
|
||||||
|
* @method handleMouseUp
|
||||||
|
*/
|
||||||
handleMouseUp(event) {
|
handleMouseUp(event) {
|
||||||
super.handleMouseUp(event);
|
super.handleMouseUp(event);
|
||||||
|
|
||||||
@ -68,10 +104,20 @@ class SeekBar extends Slider {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Move more quickly fast forward for keyboard-only users
|
||||||
|
*
|
||||||
|
* @method stepForward
|
||||||
|
*/
|
||||||
stepForward() {
|
stepForward() {
|
||||||
this.player_.currentTime(this.player_.currentTime() + 5); // more quickly fast forward for keyboard-only users
|
this.player_.currentTime(this.player_.currentTime() + 5); // more quickly fast forward for keyboard-only users
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Move more quickly rewind for keyboard-only users
|
||||||
|
*
|
||||||
|
* @method stepBack
|
||||||
|
*/
|
||||||
stepBack() {
|
stepBack() {
|
||||||
this.player_.currentTime(this.player_.currentTime() - 5); // more quickly rewind for keyboard-only users
|
this.player_.currentTime(this.player_.currentTime() - 5); // more quickly rewind for keyboard-only users
|
||||||
}
|
}
|
||||||
|
@ -1,17 +1,33 @@
|
|||||||
|
/**
|
||||||
|
* @file custom-control-spacer.js
|
||||||
|
*/
|
||||||
import Spacer from './spacer.js';
|
import Spacer from './spacer.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Spacer specifically meant to be used as an insertion point for new plugins, etc.
|
* Spacer specifically meant to be used as an insertion point for new plugins, etc.
|
||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @extends Spacer
|
||||||
* @param {Obect=} options
|
* @class CustomControlSpacer
|
||||||
*/
|
*/
|
||||||
class CustomControlSpacer extends Spacer {
|
class CustomControlSpacer extends Spacer {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-custom-control-spacer ${super.buildCSSClass()}`;
|
return `vjs-custom-control-spacer ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl({
|
return super.createEl({
|
||||||
className: this.buildCSSClass()
|
className: this.buildCSSClass()
|
||||||
|
@ -1,17 +1,34 @@
|
|||||||
|
/**
|
||||||
|
* @file spacer.js
|
||||||
|
*/
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Just an empty spacer element that can be used as an append point for plugins, etc.
|
* Just an empty spacer element that can be used as an append point for plugins, etc.
|
||||||
* Also can be used to create space between elements when necessary.
|
* Also can be used to create space between elements when necessary.
|
||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @extends Component
|
||||||
* @param {Object=} options
|
* @class Spacer
|
||||||
*/
|
*/
|
||||||
class Spacer extends Component {
|
class Spacer extends Component {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-spacer ${super.buildCSSClass()}`;
|
return `vjs-spacer ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @param {Object} props An object of properties
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl(props) {
|
createEl(props) {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: this.buildCSSClass()
|
className: this.buildCSSClass()
|
||||||
|
@ -1,7 +1,18 @@
|
|||||||
|
/**
|
||||||
|
* @file caption-settings-menu-item.js
|
||||||
|
*/
|
||||||
import TextTrackMenuItem from './text-track-menu-item.js';
|
import TextTrackMenuItem from './text-track-menu-item.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
|
|
||||||
class CaptionSettingsMenuItem extends TextTrackMenuItem {
|
/**
|
||||||
|
* The menu item for caption track settings menu
|
||||||
|
*
|
||||||
|
* @param {Player|Object} player
|
||||||
|
* @param {Object=} options
|
||||||
|
* @extends TextTrackMenuItem
|
||||||
|
* @class CaptionSettingsMenuItem
|
||||||
|
*/
|
||||||
|
class CaptionSettingsMenuItem extends TextTrackMenuItem {
|
||||||
|
|
||||||
constructor(player, options) {
|
constructor(player, options) {
|
||||||
options['track'] = {
|
options['track'] = {
|
||||||
@ -16,6 +27,11 @@ class CaptionSettingsMenuItem extends TextTrackMenuItem {
|
|||||||
this.addClass('vjs-texttrack-settings');
|
this.addClass('vjs-texttrack-settings');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle click on menu item
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
this.player().getChild('textTrackSettings').show();
|
this.player().getChild('textTrackSettings').show();
|
||||||
}
|
}
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file captions-button.js
|
||||||
|
*/
|
||||||
import TextTrackButton from './text-track-button.js';
|
import TextTrackButton from './text-track-button.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import CaptionSettingsMenuItem from './caption-settings-menu-item.js';
|
import CaptionSettingsMenuItem from './caption-settings-menu-item.js';
|
||||||
@ -5,7 +8,11 @@ import CaptionSettingsMenuItem from './caption-settings-menu-item.js';
|
|||||||
/**
|
/**
|
||||||
* The button component for toggling and selecting captions
|
* The button component for toggling and selecting captions
|
||||||
*
|
*
|
||||||
* @constructor
|
* @param {Object} player Player object
|
||||||
|
* @param {Object=} options Object of option names and values
|
||||||
|
* @param {Function=} ready Ready callback function
|
||||||
|
* @extends TextTrackButton
|
||||||
|
* @class CaptionsButton
|
||||||
*/
|
*/
|
||||||
class CaptionsButton extends TextTrackButton {
|
class CaptionsButton extends TextTrackButton {
|
||||||
|
|
||||||
@ -14,10 +21,21 @@ class CaptionsButton extends TextTrackButton {
|
|||||||
this.el_.setAttribute('aria-label','Captions Menu');
|
this.el_.setAttribute('aria-label','Captions Menu');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-captions-button ${super.buildCSSClass()}`;
|
return `vjs-captions-button ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update caption menu items
|
||||||
|
*
|
||||||
|
* @method update
|
||||||
|
*/
|
||||||
update() {
|
update() {
|
||||||
let threshold = 2;
|
let threshold = 2;
|
||||||
super.update();
|
super.update();
|
||||||
@ -34,6 +52,12 @@ class CaptionsButton extends TextTrackButton {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create caption menu items
|
||||||
|
*
|
||||||
|
* @return {Array} Array of menu items
|
||||||
|
* @method createItems
|
||||||
|
*/
|
||||||
createItems() {
|
createItems() {
|
||||||
let items = [];
|
let items = [];
|
||||||
|
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file chapters-button.js
|
||||||
|
*/
|
||||||
import TextTrackButton from './text-track-button.js';
|
import TextTrackButton from './text-track-button.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import TextTrackMenuItem from './text-track-menu-item.js';
|
import TextTrackMenuItem from './text-track-menu-item.js';
|
||||||
@ -8,12 +11,16 @@ import * as Fn from '../../utils/fn.js';
|
|||||||
import toTitleCase from '../../utils/to-title-case.js';
|
import toTitleCase from '../../utils/to-title-case.js';
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
|
|
||||||
// Chapters act much differently than other text tracks
|
|
||||||
// Cues are navigation vs. other tracks of alternative languages
|
|
||||||
/**
|
/**
|
||||||
* The button component for toggling and selecting chapters
|
* The button component for toggling and selecting chapters
|
||||||
|
* Chapters act much differently than other text tracks
|
||||||
|
* Cues are navigation vs. other tracks of alternative languages
|
||||||
*
|
*
|
||||||
* @constructor
|
* @param {Object} player Player object
|
||||||
|
* @param {Object=} options Object of option names and values
|
||||||
|
* @param {Function=} ready Ready callback function
|
||||||
|
* @extends TextTrackButton
|
||||||
|
* @class ChaptersButton
|
||||||
*/
|
*/
|
||||||
class ChaptersButton extends TextTrackButton {
|
class ChaptersButton extends TextTrackButton {
|
||||||
|
|
||||||
@ -22,11 +29,22 @@ class ChaptersButton extends TextTrackButton {
|
|||||||
this.el_.setAttribute('aria-label','Chapters Menu');
|
this.el_.setAttribute('aria-label','Chapters Menu');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-chapters-button ${super.buildCSSClass()}`;
|
return `vjs-chapters-button ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Create a menu item for each text track
|
/**
|
||||||
|
* Create a menu item for each text track
|
||||||
|
*
|
||||||
|
* @return {Array} Array of menu items
|
||||||
|
* @method createItems
|
||||||
|
*/
|
||||||
createItems() {
|
createItems() {
|
||||||
let items = [];
|
let items = [];
|
||||||
|
|
||||||
@ -48,6 +66,12 @@ class ChaptersButton extends TextTrackButton {
|
|||||||
return items;
|
return items;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create menu from chapter buttons
|
||||||
|
*
|
||||||
|
* @return {Menu} Menu of chapter buttons
|
||||||
|
* @method createMenu
|
||||||
|
*/
|
||||||
createMenu() {
|
createMenu() {
|
||||||
let tracks = this.player_.textTracks() || [];
|
let tracks = this.player_.textTracks() || [];
|
||||||
let chaptersTrack;
|
let chaptersTrack;
|
||||||
|
@ -1,9 +1,17 @@
|
|||||||
|
/**
|
||||||
|
* @file chapters-track-menu-item.js
|
||||||
|
*/
|
||||||
import MenuItem from '../../menu/menu-item.js';
|
import MenuItem from '../../menu/menu-item.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import * as Fn from '../../utils/fn.js';
|
import * as Fn from '../../utils/fn.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @constructor
|
* The chapter track menu item
|
||||||
|
*
|
||||||
|
* @param {Player|Object} player
|
||||||
|
* @param {Object=} options
|
||||||
|
* @extends MenuItem
|
||||||
|
* @class ChaptersTrackMenuItem
|
||||||
*/
|
*/
|
||||||
class ChaptersTrackMenuItem extends MenuItem {
|
class ChaptersTrackMenuItem extends MenuItem {
|
||||||
|
|
||||||
@ -22,12 +30,22 @@ class ChaptersTrackMenuItem extends MenuItem {
|
|||||||
track.addEventListener('cuechange', Fn.bind(this, this.update));
|
track.addEventListener('cuechange', Fn.bind(this, this.update));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle click on menu item
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
super.handleClick();
|
super.handleClick();
|
||||||
this.player_.currentTime(this.cue.startTime);
|
this.player_.currentTime(this.cue.startTime);
|
||||||
this.update(this.cue.startTime);
|
this.update(this.cue.startTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update chapter menu item
|
||||||
|
*
|
||||||
|
* @method update
|
||||||
|
*/
|
||||||
update() {
|
update() {
|
||||||
let cue = this.cue;
|
let cue = this.cue;
|
||||||
let currentTime = this.player_.currentTime();
|
let currentTime = this.player_.currentTime();
|
||||||
|
@ -1,10 +1,16 @@
|
|||||||
|
/**
|
||||||
|
* @file off-text-track-menu-item.js
|
||||||
|
*/
|
||||||
import TextTrackMenuItem from './text-track-menu-item.js';
|
import TextTrackMenuItem from './text-track-menu-item.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A special menu item for turning of a specific type of text track
|
* A special menu item for turning of a specific type of text track
|
||||||
*
|
*
|
||||||
* @constructor
|
* @param {Player|Object} player
|
||||||
|
* @param {Object=} options
|
||||||
|
* @extends TextTrackMenuItem
|
||||||
|
* @class OffTextTrackMenuItem
|
||||||
*/
|
*/
|
||||||
class OffTextTrackMenuItem extends TextTrackMenuItem {
|
class OffTextTrackMenuItem extends TextTrackMenuItem {
|
||||||
|
|
||||||
@ -23,6 +29,12 @@ class OffTextTrackMenuItem extends TextTrackMenuItem {
|
|||||||
this.selected(true);
|
this.selected(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle text track change
|
||||||
|
*
|
||||||
|
* @param {Object} event Event object
|
||||||
|
* @method handleTracksChange
|
||||||
|
*/
|
||||||
handleTracksChange(event){
|
handleTracksChange(event){
|
||||||
let tracks = this.player().textTracks();
|
let tracks = this.player().textTracks();
|
||||||
let selected = true;
|
let selected = true;
|
||||||
|
@ -1,10 +1,17 @@
|
|||||||
|
/**
|
||||||
|
* @file subtitles-button.js
|
||||||
|
*/
|
||||||
import TextTrackButton from './text-track-button.js';
|
import TextTrackButton from './text-track-button.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The button component for toggling and selecting subtitles
|
* The button component for toggling and selecting subtitles
|
||||||
*
|
*
|
||||||
* @constructor
|
* @param {Object} player Player object
|
||||||
|
* @param {Object=} options Object of option names and values
|
||||||
|
* @param {Function=} ready Ready callback function
|
||||||
|
* @extends TextTrackButton
|
||||||
|
* @class SubtitlesButton
|
||||||
*/
|
*/
|
||||||
class SubtitlesButton extends TextTrackButton {
|
class SubtitlesButton extends TextTrackButton {
|
||||||
|
|
||||||
@ -13,6 +20,12 @@ class SubtitlesButton extends TextTrackButton {
|
|||||||
this.el_.setAttribute('aria-label','Subtitles Menu');
|
this.el_.setAttribute('aria-label','Subtitles Menu');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-subtitles-button ${super.buildCSSClass()}`;
|
return `vjs-subtitles-button ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file text-track-button.js
|
||||||
|
*/
|
||||||
import MenuButton from '../../menu/menu-button.js';
|
import MenuButton from '../../menu/menu-button.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import * as Fn from '../../utils/fn.js';
|
import * as Fn from '../../utils/fn.js';
|
||||||
@ -7,7 +10,10 @@ import OffTextTrackMenuItem from './off-text-track-menu-item.js';
|
|||||||
/**
|
/**
|
||||||
* The base class for buttons that toggle specific text track types (e.g. subtitles)
|
* The base class for buttons that toggle specific text track types (e.g. subtitles)
|
||||||
*
|
*
|
||||||
* @constructor
|
* @param {Player|Object} player
|
||||||
|
* @param {Object=} options
|
||||||
|
* @extends MenuButton
|
||||||
|
* @class TextTrackButton
|
||||||
*/
|
*/
|
||||||
class TextTrackButton extends MenuButton {
|
class TextTrackButton extends MenuButton {
|
||||||
|
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file text-track-menu-item.js
|
||||||
|
*/
|
||||||
import MenuItem from '../../menu/menu-item.js';
|
import MenuItem from '../../menu/menu-item.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import * as Fn from '../../utils/fn.js';
|
import * as Fn from '../../utils/fn.js';
|
||||||
@ -7,7 +10,10 @@ import document from 'global/document';
|
|||||||
/**
|
/**
|
||||||
* The specific menu item type for selecting a language within a text track kind
|
* The specific menu item type for selecting a language within a text track kind
|
||||||
*
|
*
|
||||||
* @constructor
|
* @param {Player|Object} player
|
||||||
|
* @param {Object=} options
|
||||||
|
* @extends MenuItem
|
||||||
|
* @class TextTrackMenuItem
|
||||||
*/
|
*/
|
||||||
class TextTrackMenuItem extends MenuItem {
|
class TextTrackMenuItem extends MenuItem {
|
||||||
|
|
||||||
@ -58,6 +64,11 @@ class TextTrackMenuItem extends MenuItem {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle click on text track
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick(event) {
|
handleClick(event) {
|
||||||
let kind = this.track['kind'];
|
let kind = this.track['kind'];
|
||||||
let tracks = this.player_.textTracks();
|
let tracks = this.player_.textTracks();
|
||||||
@ -81,6 +92,11 @@ class TextTrackMenuItem extends MenuItem {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle text track change
|
||||||
|
*
|
||||||
|
* @method handleTracksChange
|
||||||
|
*/
|
||||||
handleTracksChange(event){
|
handleTracksChange(event){
|
||||||
this.selected(this.track['mode'] === 'showing');
|
this.selected(this.track['mode'] === 'showing');
|
||||||
}
|
}
|
||||||
|
@ -1,12 +1,17 @@
|
|||||||
|
/**
|
||||||
|
* @file current-time-display.js
|
||||||
|
*/
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import * as Dom from '../../utils/dom.js';
|
import * as Dom from '../../utils/dom.js';
|
||||||
import formatTime from '../../utils/format-time.js';
|
import formatTime from '../../utils/format-time.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Displays the current time
|
* Displays the current time
|
||||||
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Component
|
||||||
|
* @class CurrentTimeDisplay
|
||||||
*/
|
*/
|
||||||
class CurrentTimeDisplay extends Component {
|
class CurrentTimeDisplay extends Component {
|
||||||
|
|
||||||
@ -16,6 +21,12 @@ class CurrentTimeDisplay extends Component {
|
|||||||
this.on(player, 'timeupdate', this.updateContent);
|
this.on(player, 'timeupdate', this.updateContent);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
let el = super.createEl('div', {
|
let el = super.createEl('div', {
|
||||||
className: 'vjs-current-time vjs-time-control vjs-control'
|
className: 'vjs-current-time vjs-time-control vjs-control'
|
||||||
@ -31,6 +42,11 @@ class CurrentTimeDisplay extends Component {
|
|||||||
return el;
|
return el;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update current time display
|
||||||
|
*
|
||||||
|
* @method updateContent
|
||||||
|
*/
|
||||||
updateContent() {
|
updateContent() {
|
||||||
// Allows for smooth scrubbing, when player can't keep up.
|
// Allows for smooth scrubbing, when player can't keep up.
|
||||||
let time = (this.player_.scrubbing) ? this.player_.getCache().currentTime : this.player_.currentTime();
|
let time = (this.player_.scrubbing) ? this.player_.getCache().currentTime : this.player_.currentTime();
|
||||||
|
@ -1,12 +1,17 @@
|
|||||||
|
/**
|
||||||
|
* @file duration-display.js
|
||||||
|
*/
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import * as Dom from '../../utils/dom.js';
|
import * as Dom from '../../utils/dom.js';
|
||||||
import formatTime from '../../utils/format-time.js';
|
import formatTime from '../../utils/format-time.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Displays the duration
|
* Displays the duration
|
||||||
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Component
|
||||||
|
* @class DurationDisplay
|
||||||
*/
|
*/
|
||||||
class DurationDisplay extends Component {
|
class DurationDisplay extends Component {
|
||||||
|
|
||||||
@ -22,6 +27,12 @@ class DurationDisplay extends Component {
|
|||||||
this.on(player, 'loadedmetadata', this.updateContent);
|
this.on(player, 'loadedmetadata', this.updateContent);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
let el = super.createEl('div', {
|
let el = super.createEl('div', {
|
||||||
className: 'vjs-duration vjs-time-control vjs-control'
|
className: 'vjs-duration vjs-time-control vjs-control'
|
||||||
@ -37,6 +48,11 @@ class DurationDisplay extends Component {
|
|||||||
return el;
|
return el;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update duration time display
|
||||||
|
*
|
||||||
|
* @method updateContent
|
||||||
|
*/
|
||||||
updateContent() {
|
updateContent() {
|
||||||
let duration = this.player_.duration();
|
let duration = this.player_.duration();
|
||||||
if (duration) {
|
if (duration) {
|
||||||
|
@ -1,12 +1,17 @@
|
|||||||
|
/**
|
||||||
|
* @file remaining-time-display.js
|
||||||
|
*/
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import * as Dom from '../../utils/dom.js';
|
import * as Dom from '../../utils/dom.js';
|
||||||
import formatTime from '../../utils/format-time.js';
|
import formatTime from '../../utils/format-time.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Displays the time left in the video
|
* Displays the time left in the video
|
||||||
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Component
|
||||||
|
* @class RemainingTimeDisplay
|
||||||
*/
|
*/
|
||||||
class RemainingTimeDisplay extends Component {
|
class RemainingTimeDisplay extends Component {
|
||||||
|
|
||||||
@ -16,6 +21,12 @@ class RemainingTimeDisplay extends Component {
|
|||||||
this.on(player, 'timeupdate', this.updateContent);
|
this.on(player, 'timeupdate', this.updateContent);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
let el = super.createEl('div', {
|
let el = super.createEl('div', {
|
||||||
className: 'vjs-remaining-time vjs-time-control vjs-control'
|
className: 'vjs-remaining-time vjs-time-control vjs-control'
|
||||||
@ -31,6 +42,11 @@ class RemainingTimeDisplay extends Component {
|
|||||||
return el;
|
return el;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update remaining time display
|
||||||
|
*
|
||||||
|
* @method updateContent
|
||||||
|
*/
|
||||||
updateContent() {
|
updateContent() {
|
||||||
if (this.player_.duration()) {
|
if (this.player_.duration()) {
|
||||||
const localizedText = this.localize('Remaining Time');
|
const localizedText = this.localize('Remaining Time');
|
||||||
|
@ -1,16 +1,25 @@
|
|||||||
|
/**
|
||||||
|
* @file time-divider.js
|
||||||
|
*/
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The separator between the current time and duration
|
* The separator between the current time and duration.
|
||||||
*
|
|
||||||
* Can be hidden if it's not needed in the design.
|
* Can be hidden if it's not needed in the design.
|
||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Component
|
||||||
|
* @class TimeDivider
|
||||||
*/
|
*/
|
||||||
class TimeDivider extends Component {
|
class TimeDivider extends Component {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-time-control vjs-time-divider',
|
className: 'vjs-time-control vjs-time-divider',
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file volume-bar.js
|
||||||
|
*/
|
||||||
import Slider from '../../slider/slider.js';
|
import Slider from '../../slider/slider.js';
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
import * as Fn from '../../utils/fn.js';
|
import * as Fn from '../../utils/fn.js';
|
||||||
@ -11,7 +14,8 @@ import VolumeLevel from './volume-level.js';
|
|||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Slider
|
||||||
|
* @class VolumeBar
|
||||||
*/
|
*/
|
||||||
class VolumeBar extends Slider {
|
class VolumeBar extends Slider {
|
||||||
|
|
||||||
@ -21,6 +25,12 @@ class VolumeBar extends Slider {
|
|||||||
player.ready(Fn.bind(this, this.updateARIAAttributes));
|
player.ready(Fn.bind(this, this.updateARIAAttributes));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-volume-bar',
|
className: 'vjs-volume-bar',
|
||||||
@ -28,6 +38,11 @@ class VolumeBar extends Slider {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle mouse move on volume bar
|
||||||
|
*
|
||||||
|
* @method handleMouseMove
|
||||||
|
*/
|
||||||
handleMouseMove(event) {
|
handleMouseMove(event) {
|
||||||
if (this.player_.muted()) {
|
if (this.player_.muted()) {
|
||||||
this.player_.muted(false);
|
this.player_.muted(false);
|
||||||
@ -36,6 +51,12 @@ class VolumeBar extends Slider {
|
|||||||
this.player_.volume(this.calculateDistance(event));
|
this.player_.volume(this.calculateDistance(event));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get percent of volume level
|
||||||
|
*
|
||||||
|
* @retun {Number} Volume level percent
|
||||||
|
* @method getPercent
|
||||||
|
*/
|
||||||
getPercent() {
|
getPercent() {
|
||||||
if (this.player_.muted()) {
|
if (this.player_.muted()) {
|
||||||
return 0;
|
return 0;
|
||||||
@ -44,14 +65,29 @@ class VolumeBar extends Slider {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Increase volume level for keyboard users
|
||||||
|
*
|
||||||
|
* @method stepForward
|
||||||
|
*/
|
||||||
stepForward() {
|
stepForward() {
|
||||||
this.player_.volume(this.player_.volume() + 0.1);
|
this.player_.volume(this.player_.volume() + 0.1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Decrease volume level for keyboard users
|
||||||
|
*
|
||||||
|
* @method stepBack
|
||||||
|
*/
|
||||||
stepBack() {
|
stepBack() {
|
||||||
this.player_.volume(this.player_.volume() - 0.1);
|
this.player_.volume(this.player_.volume() - 0.1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update ARIA accessibility attributes
|
||||||
|
*
|
||||||
|
* @method updateARIAAttributes
|
||||||
|
*/
|
||||||
updateARIAAttributes() {
|
updateARIAAttributes() {
|
||||||
// Current value of volume bar as a percentage
|
// Current value of volume bar as a percentage
|
||||||
this.el_.setAttribute('aria-valuenow', roundFloat(this.player_.volume()*100, 2));
|
this.el_.setAttribute('aria-valuenow', roundFloat(this.player_.volume()*100, 2));
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file volume-control.js
|
||||||
|
*/
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
|
|
||||||
// Required children
|
// Required children
|
||||||
@ -8,7 +11,8 @@ import VolumeBar from './volume-bar.js';
|
|||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Component
|
||||||
|
* @class VolumeControl
|
||||||
*/
|
*/
|
||||||
class VolumeControl extends Component {
|
class VolumeControl extends Component {
|
||||||
|
|
||||||
@ -28,6 +32,12 @@ class VolumeControl extends Component {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-volume-control vjs-control'
|
className: 'vjs-volume-control vjs-control'
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file volume-level.js
|
||||||
|
*/
|
||||||
import Component from '../../component.js';
|
import Component from '../../component.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -5,10 +8,17 @@ import Component from '../../component.js';
|
|||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Component
|
||||||
|
* @class VolumeLevel
|
||||||
*/
|
*/
|
||||||
class VolumeLevel extends Component {
|
class VolumeLevel extends Component {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-volume-level',
|
className: 'vjs-volume-level',
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file volume-menu-button.js
|
||||||
|
*/
|
||||||
import Button from '../button.js';
|
import Button from '../button.js';
|
||||||
import Component from '../component.js';
|
import Component from '../component.js';
|
||||||
import Menu from '../menu/menu.js';
|
import Menu from '../menu/menu.js';
|
||||||
@ -6,8 +9,12 @@ import MuteToggle from './mute-toggle.js';
|
|||||||
import VolumeBar from './volume-control/volume-bar.js';
|
import VolumeBar from './volume-control/volume-bar.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Menu button with a popup for showing the volume slider.
|
* Button for volume menu
|
||||||
* @constructor
|
*
|
||||||
|
* @param {Player|Object} player
|
||||||
|
* @param {Object=} options
|
||||||
|
* @extends MenuButton
|
||||||
|
* @class VolumeMenuButton
|
||||||
*/
|
*/
|
||||||
class VolumeMenuButton extends MenuButton {
|
class VolumeMenuButton extends MenuButton {
|
||||||
|
|
||||||
@ -31,10 +38,22 @@ class VolumeMenuButton extends MenuButton {
|
|||||||
this.addClass('vjs-menu-button');
|
this.addClass('vjs-menu-button');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-volume-menu-button ${super.buildCSSClass()}`;
|
return `vjs-volume-menu-button ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {Menu} The volume menu button
|
||||||
|
* @method createMenu
|
||||||
|
*/
|
||||||
createMenu() {
|
createMenu() {
|
||||||
let menu = new Menu(this.player_, {
|
let menu = new Menu(this.player_, {
|
||||||
contentElType: 'div'
|
contentElType: 'div'
|
||||||
@ -56,6 +75,11 @@ class VolumeMenuButton extends MenuButton {
|
|||||||
return menu;
|
return menu;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle click on volume menu and calls super
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
MuteToggle.prototype.handleClick.call(this);
|
MuteToggle.prototype.handleClick.call(this);
|
||||||
super.handleClick();
|
super.handleClick();
|
||||||
|
@ -1,11 +1,16 @@
|
|||||||
|
/**
|
||||||
|
* @file error-display.js
|
||||||
|
*/
|
||||||
import Component from './component';
|
import Component from './component';
|
||||||
import * as Dom from './utils/dom.js';
|
import * as Dom from './utils/dom.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Display that an error has occurred making the video unplayable
|
* Display that an error has occurred making the video unplayable
|
||||||
* @param {Player|Object} player
|
*
|
||||||
* @param {Object=} options
|
* @param {Object} player Main Player
|
||||||
* @constructor
|
* @param {Object=} options Object of option names and values
|
||||||
|
* @extends Component
|
||||||
|
* @class ErrorDisplay
|
||||||
*/
|
*/
|
||||||
class ErrorDisplay extends Component {
|
class ErrorDisplay extends Component {
|
||||||
|
|
||||||
@ -16,6 +21,12 @@ class ErrorDisplay extends Component {
|
|||||||
this.on(player, 'error', this.update);
|
this.on(player, 'error', this.update);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
var el = super.createEl('div', {
|
var el = super.createEl('div', {
|
||||||
className: 'vjs-error-display'
|
className: 'vjs-error-display'
|
||||||
@ -27,6 +38,11 @@ class ErrorDisplay extends Component {
|
|||||||
return el;
|
return el;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update the error message in localized language
|
||||||
|
*
|
||||||
|
* @method update
|
||||||
|
*/
|
||||||
update() {
|
update() {
|
||||||
if (this.player().error()) {
|
if (this.player().error()) {
|
||||||
this.contentEl_.innerHTML = this.localize(this.player().error().message);
|
this.contentEl_.innerHTML = this.localize(this.player().error().message);
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file event-emitter.js
|
||||||
|
*/
|
||||||
import * as Events from './utils/events.js';
|
import * as Events from './utils/events.js';
|
||||||
|
|
||||||
var EventEmitter = function() {};
|
var EventEmitter = function() {};
|
||||||
|
@ -1,4 +1,6 @@
|
|||||||
/**
|
/*
|
||||||
|
* @file extends.js
|
||||||
|
*
|
||||||
* A combination of node inherits and babel's inherits (after transpile).
|
* A combination of node inherits and babel's inherits (after transpile).
|
||||||
* Both work the same but node adds `super_` to the subClass
|
* Both work the same but node adds `super_` to the subClass
|
||||||
* and Bable adds the superClass as __proto__. Both seem useful.
|
* and Bable adds the superClass as __proto__. Both seem useful.
|
||||||
@ -23,18 +25,17 @@ const _inherits = function (subClass, superClass) {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Function for subclassing using the same inheritance that
|
* Function for subclassing using the same inheritance that
|
||||||
* videojs uses internally
|
* videojs uses internally
|
||||||
*
|
* ```js
|
||||||
* ```
|
|
||||||
* var Button = videojs.getComponent('Button');
|
* var Button = videojs.getComponent('Button');
|
||||||
*
|
* ```
|
||||||
|
* ```js
|
||||||
* var MyButton = videojs.extends(Button, {
|
* var MyButton = videojs.extends(Button, {
|
||||||
* constructor: function(player, options) {
|
* constructor: function(player, options) {
|
||||||
* Button.call(this, player, options);
|
* Button.call(this, player, options);
|
||||||
* },
|
* },
|
||||||
*
|
|
||||||
* onClick: function() {
|
* onClick: function() {
|
||||||
* // doSomething
|
* // doSomething
|
||||||
* }
|
* }
|
||||||
|
@ -1,6 +1,9 @@
|
|||||||
|
/**
|
||||||
|
* @file fullscreen-api.js
|
||||||
|
*/
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Store the browser-specific methods for the fullscreen API
|
* Store the browser-specific methods for the fullscreen API
|
||||||
* @type {Object|undefined}
|
* @type {Object|undefined}
|
||||||
* @private
|
* @private
|
||||||
|
@ -1,12 +1,16 @@
|
|||||||
|
/**
|
||||||
|
* @file global-options.js
|
||||||
|
*/
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
let navigator = window.navigator;
|
let navigator = window.navigator;
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Global Player instance options, surfaced from Player.prototype.options_
|
* Global Player instance options, surfaced from Player.prototype.options_
|
||||||
* options = Player.prototype.options_
|
* options = Player.prototype.options_
|
||||||
* All options should use string keys so they avoid
|
* All options should use string keys so they avoid
|
||||||
* renaming by closure compiler
|
* renaming by closure compiler
|
||||||
|
*
|
||||||
* @type {Object}
|
* @type {Object}
|
||||||
*/
|
*/
|
||||||
export default {
|
export default {
|
||||||
|
@ -1,15 +1,23 @@
|
|||||||
|
/**
|
||||||
|
* @file loading-spinner.js
|
||||||
|
*/
|
||||||
import Component from './component';
|
import Component from './component';
|
||||||
|
|
||||||
/* Loading Spinner
|
/* Loading Spinner
|
||||||
================================================================================ */
|
================================================================================ */
|
||||||
/**
|
/**
|
||||||
* Loading spinner for waiting events
|
* Loading spinner for waiting events
|
||||||
* @param {Player|Object} player
|
*
|
||||||
* @param {Object=} options
|
* @extends Component
|
||||||
* @class
|
* @class LoadingSpinner
|
||||||
* @constructor
|
|
||||||
*/
|
*/
|
||||||
class LoadingSpinner extends Component {
|
class LoadingSpinner extends Component {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-loading-spinner'
|
className: 'vjs-loading-spinner'
|
||||||
|
@ -1,7 +1,11 @@
|
|||||||
|
/**
|
||||||
|
* @file media-error.js
|
||||||
|
*/
|
||||||
import assign from 'object.assign';
|
import assign from 'object.assign';
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Custom MediaError to mimic the HTML5 MediaError
|
* Custom MediaError to mimic the HTML5 MediaError
|
||||||
|
*
|
||||||
* @param {Number} code The media error code
|
* @param {Number} code The media error code
|
||||||
*/
|
*/
|
||||||
let MediaError = function(code){
|
let MediaError = function(code){
|
||||||
@ -19,29 +23,32 @@ let MediaError = function(code){
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* The error code that refers two one of the defined
|
* The error code that refers two one of the defined
|
||||||
* MediaError types
|
* MediaError types
|
||||||
|
*
|
||||||
* @type {Number}
|
* @type {Number}
|
||||||
*/
|
*/
|
||||||
MediaError.prototype.code = 0;
|
MediaError.prototype.code = 0;
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* An optional message to be shown with the error.
|
* An optional message to be shown with the error.
|
||||||
* Message is not part of the HTML5 video spec
|
* Message is not part of the HTML5 video spec
|
||||||
* but allows for more informative custom errors.
|
* but allows for more informative custom errors.
|
||||||
|
*
|
||||||
* @type {String}
|
* @type {String}
|
||||||
*/
|
*/
|
||||||
MediaError.prototype.message = '';
|
MediaError.prototype.message = '';
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* An optional status code that can be set by plugins
|
* An optional status code that can be set by plugins
|
||||||
* to allow even more detail about the error.
|
* to allow even more detail about the error.
|
||||||
* For example the HLS plugin might provide the specific
|
* For example the HLS plugin might provide the specific
|
||||||
* HTTP status code that was returned when the error
|
* HTTP status code that was returned when the error
|
||||||
* occurred, then allowing a custom error overlay
|
* occurred, then allowing a custom error overlay
|
||||||
* to display more information.
|
* to display more information.
|
||||||
* @type {[type]}
|
*
|
||||||
|
* @type {Array}
|
||||||
*/
|
*/
|
||||||
MediaError.prototype.status = null;
|
MediaError.prototype.status = null;
|
||||||
|
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file menu-button.js
|
||||||
|
*/
|
||||||
import Button from '../button.js';
|
import Button from '../button.js';
|
||||||
import Component from '../component.js';
|
import Component from '../component.js';
|
||||||
import Menu from './menu.js';
|
import Menu from './menu.js';
|
||||||
@ -7,9 +10,11 @@ import toTitleCase from '../utils/to-title-case.js';
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* A button class with a popup menu
|
* A button class with a popup menu
|
||||||
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Button
|
||||||
|
* @class MenuButton
|
||||||
*/
|
*/
|
||||||
class MenuButton extends Button {
|
class MenuButton extends Button {
|
||||||
|
|
||||||
@ -23,6 +28,11 @@ class MenuButton extends Button {
|
|||||||
this.el_.setAttribute('role', 'button');
|
this.el_.setAttribute('role', 'button');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update menu
|
||||||
|
*
|
||||||
|
* @method update
|
||||||
|
*/
|
||||||
update() {
|
update() {
|
||||||
let menu = this.createMenu();
|
let menu = this.createMenu();
|
||||||
|
|
||||||
@ -35,6 +45,7 @@ class MenuButton extends Button {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Track the state of the menu button
|
* Track the state of the menu button
|
||||||
|
*
|
||||||
* @type {Boolean}
|
* @type {Boolean}
|
||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
@ -47,6 +58,12 @@ class MenuButton extends Button {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create menu
|
||||||
|
*
|
||||||
|
* @return {Menu} The constructed menu
|
||||||
|
* @method createMenu
|
||||||
|
*/
|
||||||
createMenu() {
|
createMenu() {
|
||||||
var menu = new Menu(this.player_);
|
var menu = new Menu(this.player_);
|
||||||
|
|
||||||
@ -73,33 +90,64 @@ class MenuButton extends Button {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Create the list of menu items. Specific to each subclass.
|
* Create the list of menu items. Specific to each subclass.
|
||||||
|
*
|
||||||
|
* @method createItems
|
||||||
*/
|
*/
|
||||||
createItems(){}
|
createItems(){}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: this.buildCSSClass()
|
className: this.buildCSSClass()
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @inheritDoc */
|
/**
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @return {String} The constructed class name
|
||||||
|
* @method buildCSSClass
|
||||||
|
*/
|
||||||
buildCSSClass() {
|
buildCSSClass() {
|
||||||
return `vjs-menu-button ${super.buildCSSClass()}`;
|
return `vjs-menu-button ${super.buildCSSClass()}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Focus - Add keyboard functionality to element
|
/**
|
||||||
// This function is not needed anymore. Instead, the keyboard functionality is handled by
|
* Focus - Add keyboard functionality to element
|
||||||
// treating the button as triggering a submenu. When the button is pressed, the submenu
|
* This function is not needed anymore. Instead, the
|
||||||
// appears. Pressing the button again makes the submenu disappear.
|
* keyboard functionality is handled by
|
||||||
|
* treating the button as triggering a submenu.
|
||||||
|
* When the button is pressed, the submenu
|
||||||
|
* appears. Pressing the button again makes
|
||||||
|
* the submenu disappear.
|
||||||
|
*
|
||||||
|
* @method handleFocus
|
||||||
|
*/
|
||||||
handleFocus() {}
|
handleFocus() {}
|
||||||
|
|
||||||
// Can't turn off list display that we turned on with focus, because list would go away.
|
/**
|
||||||
|
* Can't turn off list display that we turned
|
||||||
|
* on with focus, because list would go away.
|
||||||
|
*
|
||||||
|
* @method handleBlur
|
||||||
|
*/
|
||||||
handleBlur() {}
|
handleBlur() {}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* When you click the button it adds focus, which
|
||||||
|
* will show the menu indefinitely.
|
||||||
|
* So we'll remove focus when the mouse leaves the button.
|
||||||
|
* Focus is needed for tab navigation.
|
||||||
|
* Allow sub components to stack CSS class names
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
// When you click the button it adds focus, which will show the menu indefinitely.
|
|
||||||
// So we'll remove focus when the mouse leaves the button.
|
|
||||||
// Focus is needed for tab navigation.
|
|
||||||
this.one('mouseout', Fn.bind(this, function(){
|
this.one('mouseout', Fn.bind(this, function(){
|
||||||
this.menu.unlockShowing();
|
this.menu.unlockShowing();
|
||||||
this.el_.blur();
|
this.el_.blur();
|
||||||
@ -111,6 +159,12 @@ class MenuButton extends Button {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle key press on menu
|
||||||
|
*
|
||||||
|
* @param {Object} Key press event
|
||||||
|
* @method handleKeyPress
|
||||||
|
*/
|
||||||
handleKeyPress(event) {
|
handleKeyPress(event) {
|
||||||
|
|
||||||
// Check for space bar (32) or enter (13) keys
|
// Check for space bar (32) or enter (13) keys
|
||||||
@ -130,6 +184,11 @@ class MenuButton extends Button {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Makes changes based on button pressed
|
||||||
|
*
|
||||||
|
* @method pressButton
|
||||||
|
*/
|
||||||
pressButton() {
|
pressButton() {
|
||||||
this.buttonPressed_ = true;
|
this.buttonPressed_ = true;
|
||||||
this.menu.lockShowing();
|
this.menu.lockShowing();
|
||||||
@ -139,6 +198,11 @@ class MenuButton extends Button {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Makes changes based on button unpressed
|
||||||
|
*
|
||||||
|
* @method unpressButton
|
||||||
|
*/
|
||||||
unpressButton() {
|
unpressButton() {
|
||||||
this.buttonPressed_ = false;
|
this.buttonPressed_ = false;
|
||||||
this.menu.unlockShowing();
|
this.menu.unlockShowing();
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file menu-item.js
|
||||||
|
*/
|
||||||
import Button from '../button.js';
|
import Button from '../button.js';
|
||||||
import Component from '../component.js';
|
import Component from '../component.js';
|
||||||
import assign from 'object.assign';
|
import assign from 'object.assign';
|
||||||
@ -7,8 +10,8 @@ import assign from 'object.assign';
|
|||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @class
|
* @extends Button
|
||||||
* @constructor
|
* @class MenuItem
|
||||||
*/
|
*/
|
||||||
class MenuItem extends Button {
|
class MenuItem extends Button {
|
||||||
|
|
||||||
@ -17,7 +20,14 @@ class MenuItem extends Button {
|
|||||||
this.selected(options['selected']);
|
this.selected(options['selected']);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @inheritDoc */
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @param {String=} type Desc
|
||||||
|
* @param {Object=} props Desc
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl(type, props) {
|
createEl(type, props) {
|
||||||
return super.createEl('li', assign({
|
return super.createEl('li', assign({
|
||||||
className: 'vjs-menu-item',
|
className: 'vjs-menu-item',
|
||||||
@ -27,6 +37,8 @@ class MenuItem extends Button {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Handle a click on the menu item, and set it to selected
|
* Handle a click on the menu item, and set it to selected
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
*/
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
this.selected(true);
|
this.selected(true);
|
||||||
@ -34,7 +46,9 @@ class MenuItem extends Button {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Set this menu item as selected or not
|
* Set this menu item as selected or not
|
||||||
|
*
|
||||||
* @param {Boolean} selected
|
* @param {Boolean} selected
|
||||||
|
* @method selected
|
||||||
*/
|
*/
|
||||||
selected(selected) {
|
selected(selected) {
|
||||||
if (selected) {
|
if (selected) {
|
||||||
|
@ -1,24 +1,25 @@
|
|||||||
|
/**
|
||||||
|
* @file menu.js
|
||||||
|
*/
|
||||||
import Component from '../component.js';
|
import Component from '../component.js';
|
||||||
import * as Dom from '../utils/dom.js';
|
import * as Dom from '../utils/dom.js';
|
||||||
import * as Fn from '../utils/fn.js';
|
import * as Fn from '../utils/fn.js';
|
||||||
import * as Events from '../utils/events.js';
|
import * as Events from '../utils/events.js';
|
||||||
|
|
||||||
/* Menu
|
|
||||||
================================================================================ */
|
|
||||||
/**
|
/**
|
||||||
* The Menu component is used to build pop up menus, including subtitle and
|
* The Menu component is used to build pop up menus, including subtitle and
|
||||||
* captions selection menus.
|
* captions selection menus.
|
||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @extends Component
|
||||||
* @param {Object=} options
|
* @class Menu
|
||||||
* @class
|
|
||||||
* @constructor
|
|
||||||
*/
|
*/
|
||||||
class Menu extends Component {
|
class Menu extends Component {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add a menu item to the menu
|
* Add a menu item to the menu
|
||||||
|
*
|
||||||
* @param {Object|String} component Component or component type to add
|
* @param {Object|String} component Component or component type to add
|
||||||
|
* @method addItem
|
||||||
*/
|
*/
|
||||||
addItem(component) {
|
addItem(component) {
|
||||||
this.addChild(component);
|
this.addChild(component);
|
||||||
@ -27,6 +28,12 @@ class Menu extends Component {
|
|||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
let contentElType = this.options_.contentElType || 'ul';
|
let contentElType = this.options_.contentElType || 'ul';
|
||||||
this.contentEl_ = Dom.createEl(contentElType, {
|
this.contentEl_ = Dom.createEl(contentElType, {
|
||||||
|
539
src/js/player.js
539
src/js/player.js
File diff suppressed because it is too large
Load Diff
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file plugins.js
|
||||||
|
*/
|
||||||
import Player from './player.js';
|
import Player from './player.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -5,6 +8,7 @@ import Player from './player.js';
|
|||||||
*
|
*
|
||||||
* @param {String} name The name of the plugin
|
* @param {String} name The name of the plugin
|
||||||
* @param {Function} init The function that is run when the player inits
|
* @param {Function} init The function that is run when the player inits
|
||||||
|
* @method plugin
|
||||||
*/
|
*/
|
||||||
var plugin = function(name, init){
|
var plugin = function(name, init){
|
||||||
Player.prototype[name] = init;
|
Player.prototype[name] = init;
|
||||||
|
@ -1,17 +1,19 @@
|
|||||||
|
/**
|
||||||
|
* @file poster-image.js
|
||||||
|
*/
|
||||||
import Button from './button.js';
|
import Button from './button.js';
|
||||||
import Component from './component.js';
|
import Component from './component.js';
|
||||||
import * as Fn from './utils/fn.js';
|
import * as Fn from './utils/fn.js';
|
||||||
import * as Dom from './utils/dom.js';
|
import * as Dom from './utils/dom.js';
|
||||||
import * as browser from './utils/browser.js';
|
import * as browser from './utils/browser.js';
|
||||||
|
|
||||||
/* Poster Image
|
|
||||||
================================================================================ */
|
|
||||||
/**
|
/**
|
||||||
* The component that handles showing the poster image.
|
* The component that handles showing the poster image.
|
||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Button
|
||||||
|
* @class PosterImage
|
||||||
*/
|
*/
|
||||||
class PosterImage extends Button {
|
class PosterImage extends Button {
|
||||||
|
|
||||||
@ -24,6 +26,8 @@ class PosterImage extends Button {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Clean up the poster image
|
* Clean up the poster image
|
||||||
|
*
|
||||||
|
* @method dispose
|
||||||
*/
|
*/
|
||||||
dispose() {
|
dispose() {
|
||||||
this.player().off('posterchange', this.update);
|
this.player().off('posterchange', this.update);
|
||||||
@ -31,8 +35,10 @@ class PosterImage extends Button {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create the poster image element
|
* Create the poster's image element
|
||||||
|
*
|
||||||
* @return {Element}
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
*/
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
let el = Dom.createEl('div', {
|
let el = Dom.createEl('div', {
|
||||||
@ -56,6 +62,8 @@ class PosterImage extends Button {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Event handler for updates to the player's poster source
|
* Event handler for updates to the player's poster source
|
||||||
|
*
|
||||||
|
* @method update
|
||||||
*/
|
*/
|
||||||
update() {
|
update() {
|
||||||
let url = this.player().poster();
|
let url = this.player().poster();
|
||||||
@ -73,6 +81,9 @@ class PosterImage extends Button {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the poster source depending on the display method
|
* Set the poster source depending on the display method
|
||||||
|
*
|
||||||
|
* @param {String} url The URL to the poster source
|
||||||
|
* @method setSrc
|
||||||
*/
|
*/
|
||||||
setSrc(url) {
|
setSrc(url) {
|
||||||
if (this.fallbackImg_) {
|
if (this.fallbackImg_) {
|
||||||
@ -91,6 +102,8 @@ class PosterImage extends Button {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Event handler for clicks on the poster image
|
* Event handler for clicks on the poster image
|
||||||
|
*
|
||||||
|
* @method handleClick
|
||||||
*/
|
*/
|
||||||
handleClick() {
|
handleClick() {
|
||||||
// We don't want a click to trigger playback when controls are disabled
|
// We don't want a click to trigger playback when controls are disabled
|
||||||
|
@ -1,3 +1,9 @@
|
|||||||
|
/**
|
||||||
|
* @file setup.js
|
||||||
|
*
|
||||||
|
* Functions for automatically setting up a player
|
||||||
|
* based on the data-setup attribute of the video tag
|
||||||
|
*/
|
||||||
import * as Events from './utils/events.js';
|
import * as Events from './utils/events.js';
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
@ -5,10 +11,6 @@ import window from 'global/window';
|
|||||||
let _windowLoaded = false;
|
let _windowLoaded = false;
|
||||||
let videojs;
|
let videojs;
|
||||||
|
|
||||||
/**
|
|
||||||
* @fileoverview Functions for automatically setting up a player
|
|
||||||
* based on the data-setup attribute of the video tag
|
|
||||||
*/
|
|
||||||
|
|
||||||
// Automatically set up any tags that have a data-setup attribute
|
// Automatically set up any tags that have a data-setup attribute
|
||||||
var autoSetup = function(){
|
var autoSetup = function(){
|
||||||
|
@ -1,17 +1,19 @@
|
|||||||
|
/**
|
||||||
|
* @file slider.js
|
||||||
|
*/
|
||||||
import Component from '../component.js';
|
import Component from '../component.js';
|
||||||
import * as Dom from '../utils/dom.js';
|
import * as Dom from '../utils/dom.js';
|
||||||
import roundFloat from '../utils/round-float.js';
|
import roundFloat from '../utils/round-float.js';
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
import assign from 'object.assign';
|
import assign from 'object.assign';
|
||||||
|
|
||||||
/* Slider
|
|
||||||
================================================================================ */
|
|
||||||
/**
|
/**
|
||||||
* The base functionality for sliders like the volume bar and seek bar
|
* The base functionality for sliders like the volume bar and seek bar
|
||||||
*
|
*
|
||||||
* @param {Player|Object} player
|
* @param {Player|Object} player
|
||||||
* @param {Object=} options
|
* @param {Object=} options
|
||||||
* @constructor
|
* @extends Component
|
||||||
|
* @class Slider
|
||||||
*/
|
*/
|
||||||
class Slider extends Component {
|
class Slider extends Component {
|
||||||
|
|
||||||
@ -35,6 +37,14 @@ class Slider extends Component {
|
|||||||
this.on(player, this.playerEvent, this.update);
|
this.on(player, this.playerEvent, this.update);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @param {String} type Type of element to create
|
||||||
|
* @param {Object=} props List of properties in Object form
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl(type, props={}) {
|
createEl(type, props={}) {
|
||||||
// Add the slider element class to all sub classes
|
// Add the slider element class to all sub classes
|
||||||
props.className = props.className + ' vjs-slider';
|
props.className = props.className + ' vjs-slider';
|
||||||
@ -49,6 +59,12 @@ class Slider extends Component {
|
|||||||
return super.createEl(type, props);
|
return super.createEl(type, props);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle mouse down on slider
|
||||||
|
*
|
||||||
|
* @param {Object} event Mouse down event object
|
||||||
|
* @method handleMouseDown
|
||||||
|
*/
|
||||||
handleMouseDown(event) {
|
handleMouseDown(event) {
|
||||||
event.preventDefault();
|
event.preventDefault();
|
||||||
Dom.blockTextSelection();
|
Dom.blockTextSelection();
|
||||||
@ -62,9 +78,18 @@ class Slider extends Component {
|
|||||||
this.handleMouseMove(event);
|
this.handleMouseMove(event);
|
||||||
}
|
}
|
||||||
|
|
||||||
// To be overridden by a subclass
|
/**
|
||||||
|
* To be overridden by a subclass
|
||||||
|
*
|
||||||
|
* @method handleMouseMove
|
||||||
|
*/
|
||||||
handleMouseMove() {}
|
handleMouseMove() {}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle mouse up on Slider
|
||||||
|
*
|
||||||
|
* @method handleMouseUp
|
||||||
|
*/
|
||||||
handleMouseUp() {
|
handleMouseUp() {
|
||||||
Dom.unblockTextSelection();
|
Dom.unblockTextSelection();
|
||||||
this.removeClass('vjs-sliding');
|
this.removeClass('vjs-sliding');
|
||||||
@ -77,6 +102,11 @@ class Slider extends Component {
|
|||||||
this.update();
|
this.update();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update slider
|
||||||
|
*
|
||||||
|
* @method update
|
||||||
|
*/
|
||||||
update() {
|
update() {
|
||||||
// In VolumeBar init we have a setTimeout for update that pops and update to the end of the
|
// In VolumeBar init we have a setTimeout for update that pops and update to the end of the
|
||||||
// execution stack. The player is destroyed before then update will cause an error
|
// execution stack. The player is destroyed before then update will cause an error
|
||||||
@ -110,6 +140,12 @@ class Slider extends Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Calculate distance for slider
|
||||||
|
*
|
||||||
|
* @param {Object} event Event object
|
||||||
|
* @method calculateDistance
|
||||||
|
*/
|
||||||
calculateDistance(event){
|
calculateDistance(event){
|
||||||
let el = this.el_;
|
let el = this.el_;
|
||||||
let box = Dom.findElPosition(el);
|
let box = Dom.findElPosition(el);
|
||||||
@ -160,10 +196,21 @@ class Slider extends Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle on focus for slider
|
||||||
|
*
|
||||||
|
* @method handleFocus
|
||||||
|
*/
|
||||||
handleFocus() {
|
handleFocus() {
|
||||||
this.on(document, 'keydown', this.handleKeyPress);
|
this.on(document, 'keydown', this.handleKeyPress);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle key press for slider
|
||||||
|
*
|
||||||
|
* @param {Object} event Event object
|
||||||
|
* @method handleKeyPress
|
||||||
|
*/
|
||||||
handleKeyPress(event) {
|
handleKeyPress(event) {
|
||||||
if (event.which === 37 || event.which === 40) { // Left and Down Arrows
|
if (event.which === 37 || event.which === 40) { // Left and Down Arrows
|
||||||
event.preventDefault();
|
event.preventDefault();
|
||||||
@ -174,6 +221,11 @@ class Slider extends Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Handle on blur for slider
|
||||||
|
*
|
||||||
|
* @method handleBlur
|
||||||
|
*/
|
||||||
handleBlur() {
|
handleBlur() {
|
||||||
this.off(document, 'keydown', this.handleKeyPress);
|
this.off(document, 'keydown', this.handleKeyPress);
|
||||||
}
|
}
|
||||||
@ -181,13 +233,22 @@ class Slider extends Component {
|
|||||||
/**
|
/**
|
||||||
* Listener for click events on slider, used to prevent clicks
|
* Listener for click events on slider, used to prevent clicks
|
||||||
* from bubbling up to parent elements like button menus.
|
* from bubbling up to parent elements like button menus.
|
||||||
* @param {Object} event Event object
|
*
|
||||||
|
* @param {Object} event Event object
|
||||||
|
* @method handleClick
|
||||||
*/
|
*/
|
||||||
handleClick(event) {
|
handleClick(event) {
|
||||||
event.stopImmediatePropagation();
|
event.stopImmediatePropagation();
|
||||||
event.preventDefault();
|
event.preventDefault();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get/set if slider is horizontal for vertical
|
||||||
|
*
|
||||||
|
* @param {Boolean} bool True if slider is vertical, false is horizontal
|
||||||
|
* @return {Boolean} True if slider is vertical, false is horizontal
|
||||||
|
* @method vertical
|
||||||
|
*/
|
||||||
vertical(bool) {
|
vertical(bool) {
|
||||||
if (bool === undefined) {
|
if (bool === undefined) {
|
||||||
return this.vertical_ || false;
|
return this.vertical_ || false;
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file flash-rtmp.js
|
||||||
|
*/
|
||||||
function FlashRtmpDecorator(Flash) {
|
function FlashRtmpDecorator(Flash) {
|
||||||
Flash.streamingFormats = {
|
Flash.streamingFormats = {
|
||||||
'rtmp/mp4': 'MP4',
|
'rtmp/mp4': 'MP4',
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
/**
|
/**
|
||||||
* @fileoverview VideoJS-SWF - Custom Flash Player with HTML5-ish API
|
* @file flash.js
|
||||||
|
* VideoJS-SWF - Custom Flash Player with HTML5-ish API
|
||||||
* https://github.com/zencoder/video-js-swf
|
* https://github.com/zencoder/video-js-swf
|
||||||
* Not using setupTriggers. Using global onEvent func to distribute events
|
* Not using setupTriggers. Using global onEvent func to distribute events
|
||||||
*/
|
*/
|
||||||
@ -17,10 +18,10 @@ let navigator = window.navigator;
|
|||||||
/**
|
/**
|
||||||
* Flash Media Controller - Wrapper for fallback SWF API
|
* Flash Media Controller - Wrapper for fallback SWF API
|
||||||
*
|
*
|
||||||
* @param {Player} player
|
* @param {Object=} options Object of option names and values
|
||||||
* @param {Object=} options
|
* @param {Function=} ready Ready callback function
|
||||||
* @param {Function=} ready
|
* @extends Tech
|
||||||
* @constructor
|
* @class Flash
|
||||||
*/
|
*/
|
||||||
class Flash extends Tech {
|
class Flash extends Tech {
|
||||||
|
|
||||||
@ -55,6 +56,12 @@ class Flash extends Tech {
|
|||||||
window.videojs.Flash.onError = Flash.onError;
|
window.videojs.Flash.onError = Flash.onError;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
let options = this.options_;
|
let options = this.options_;
|
||||||
|
|
||||||
@ -96,14 +103,31 @@ class Flash extends Tech {
|
|||||||
return this.el_;
|
return this.el_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Play for flash tech
|
||||||
|
*
|
||||||
|
* @method play
|
||||||
|
*/
|
||||||
play() {
|
play() {
|
||||||
this.el_.vjs_play();
|
this.el_.vjs_play();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pause for flash tech
|
||||||
|
*
|
||||||
|
* @method pause
|
||||||
|
*/
|
||||||
pause() {
|
pause() {
|
||||||
this.el_.vjs_pause();
|
this.el_.vjs_pause();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get/set video
|
||||||
|
*
|
||||||
|
* @param {Object=} src Source object
|
||||||
|
* @return {Object}
|
||||||
|
* @method src
|
||||||
|
*/
|
||||||
src(src) {
|
src(src) {
|
||||||
if (src === undefined) {
|
if (src === undefined) {
|
||||||
return this.currentSrc();
|
return this.currentSrc();
|
||||||
@ -113,6 +137,13 @@ class Flash extends Tech {
|
|||||||
return this.setSrc(src);
|
return this.setSrc(src);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set video
|
||||||
|
*
|
||||||
|
* @param {Object=} src Source object
|
||||||
|
* @deprecated
|
||||||
|
* @method setSrc
|
||||||
|
*/
|
||||||
setSrc(src) {
|
setSrc(src) {
|
||||||
// Make sure source URL is absolute.
|
// Make sure source URL is absolute.
|
||||||
src = Url.getAbsoluteURL(src);
|
src = Url.getAbsoluteURL(src);
|
||||||
@ -126,12 +157,25 @@ class Flash extends Tech {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set current time
|
||||||
|
*
|
||||||
|
* @param {Number} time Current time of video
|
||||||
|
* @method setCurrentTime
|
||||||
|
*/
|
||||||
setCurrentTime(time) {
|
setCurrentTime(time) {
|
||||||
this.lastSeekTarget_ = time;
|
this.lastSeekTarget_ = time;
|
||||||
this.el_.vjs_setProperty('currentTime', time);
|
this.el_.vjs_setProperty('currentTime', time);
|
||||||
super.setCurrentTime();
|
super.setCurrentTime();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get current time
|
||||||
|
*
|
||||||
|
* @param {Number=} time Current time of video
|
||||||
|
* @return {Number} Current time
|
||||||
|
* @method currentTime
|
||||||
|
*/
|
||||||
currentTime(time) {
|
currentTime(time) {
|
||||||
// when seeking make the reported time keep up with the requested time
|
// when seeking make the reported time keep up with the requested time
|
||||||
// by reading the time we're seeking to
|
// by reading the time we're seeking to
|
||||||
@ -141,6 +185,11 @@ class Flash extends Tech {
|
|||||||
return this.el_.vjs_getProperty('currentTime');
|
return this.el_.vjs_getProperty('currentTime');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get current source
|
||||||
|
*
|
||||||
|
* @method currentSrc
|
||||||
|
*/
|
||||||
currentSrc() {
|
currentSrc() {
|
||||||
if (this.currentSource_) {
|
if (this.currentSource_) {
|
||||||
return this.currentSource_.src;
|
return this.currentSource_.src;
|
||||||
@ -149,17 +198,37 @@ class Flash extends Tech {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Load media into player
|
||||||
|
*
|
||||||
|
* @method load
|
||||||
|
*/
|
||||||
load() {
|
load() {
|
||||||
this.el_.vjs_load();
|
this.el_.vjs_load();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get poster
|
||||||
|
*
|
||||||
|
* @method poster
|
||||||
|
*/
|
||||||
poster() {
|
poster() {
|
||||||
this.el_.vjs_getProperty('poster');
|
this.el_.vjs_getProperty('poster');
|
||||||
}
|
}
|
||||||
|
|
||||||
// poster images are not handled by the Flash tech so make this a no-op
|
/**
|
||||||
|
* Poster images are not handled by the Flash tech so make this a no-op
|
||||||
|
*
|
||||||
|
* @method setPoster
|
||||||
|
*/
|
||||||
setPoster() {}
|
setPoster() {}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Determine if can seek in media
|
||||||
|
*
|
||||||
|
* @return {TimeRangeObject}
|
||||||
|
* @method seekable
|
||||||
|
*/
|
||||||
seekable() {
|
seekable() {
|
||||||
const duration = this.duration();
|
const duration = this.duration();
|
||||||
if (duration === 0) {
|
if (duration === 0) {
|
||||||
@ -168,14 +237,36 @@ class Flash extends Tech {
|
|||||||
return createTimeRange(0, duration);
|
return createTimeRange(0, duration);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get buffered time range
|
||||||
|
*
|
||||||
|
* @return {TimeRangeObject}
|
||||||
|
* @method buffered
|
||||||
|
*/
|
||||||
buffered() {
|
buffered() {
|
||||||
return createTimeRange(0, this.el_.vjs_getProperty('buffered'));
|
return createTimeRange(0, this.el_.vjs_getProperty('buffered'));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get fullscreen support -
|
||||||
|
* Flash does not allow fullscreen through javascript
|
||||||
|
* so always returns false
|
||||||
|
*
|
||||||
|
* @return {Boolean} false
|
||||||
|
* @method supportsFullScreen
|
||||||
|
*/
|
||||||
supportsFullScreen() {
|
supportsFullScreen() {
|
||||||
return false; // Flash does not allow fullscreen through javascript
|
return false; // Flash does not allow fullscreen through javascript
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Request to enter fullscreen
|
||||||
|
* Flash does not allow fullscreen through javascript
|
||||||
|
* so always returns false
|
||||||
|
*
|
||||||
|
* @return {Boolean} false
|
||||||
|
* @method enterFullScreen
|
||||||
|
*/
|
||||||
enterFullScreen() {
|
enterFullScreen() {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -217,16 +308,18 @@ Flash.isSupported = function(){
|
|||||||
// Add Source Handler pattern functions to this tech
|
// Add Source Handler pattern functions to this tech
|
||||||
Tech.withSourceHandlers(Flash);
|
Tech.withSourceHandlers(Flash);
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* The default native source handler.
|
* The default native source handler.
|
||||||
* This simply passes the source to the video element. Nothing fancy.
|
* This simply passes the source to the video element. Nothing fancy.
|
||||||
|
*
|
||||||
* @param {Object} source The source object
|
* @param {Object} source The source object
|
||||||
* @param {Flash} tech The instance of the Flash tech
|
* @param {Flash} tech The instance of the Flash tech
|
||||||
*/
|
*/
|
||||||
Flash.nativeSourceHandler = {};
|
Flash.nativeSourceHandler = {};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Check Flash can handle the source natively
|
* Check Flash can handle the source natively
|
||||||
|
*
|
||||||
* @param {Object} source The source object
|
* @param {Object} source The source object
|
||||||
* @return {String} 'probably', 'maybe', or '' (empty string)
|
* @return {String} 'probably', 'maybe', or '' (empty string)
|
||||||
*/
|
*/
|
||||||
@ -255,10 +348,11 @@ Flash.nativeSourceHandler.canHandleSource = function(source){
|
|||||||
return '';
|
return '';
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Pass the source to the flash object
|
* Pass the source to the flash object
|
||||||
* Adaptive source handlers will have more complicated workflows before passing
|
* Adaptive source handlers will have more complicated workflows before passing
|
||||||
* video data to the video element
|
* video data to the video element
|
||||||
|
*
|
||||||
* @param {Object} source The source object
|
* @param {Object} source The source object
|
||||||
* @param {Flash} tech The instance of the Flash tech
|
* @param {Flash} tech The instance of the Flash tech
|
||||||
*/
|
*/
|
||||||
@ -266,7 +360,7 @@ Flash.nativeSourceHandler.handleSource = function(source, tech){
|
|||||||
tech.setSrc(source.src);
|
tech.setSrc(source.src);
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Clean up the source handler when disposing the player or switching sources..
|
* Clean up the source handler when disposing the player or switching sources..
|
||||||
* (no cleanup is needed when supporting the format natively)
|
* (no cleanup is needed when supporting the format natively)
|
||||||
*/
|
*/
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
/**
|
/**
|
||||||
* @fileoverview HTML5 Media Controller - Wrapper for HTML5 Media API
|
* @file html5.js
|
||||||
|
* HTML5 Media Controller - Wrapper for HTML5 Media API
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import Tech from './tech.js';
|
import Tech from './tech.js';
|
||||||
@ -16,10 +17,11 @@ import mergeOptions from '../utils/merge-options.js';
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* HTML5 Media Controller - Wrapper for HTML5 Media API
|
* HTML5 Media Controller - Wrapper for HTML5 Media API
|
||||||
* @param {Player|Object} player
|
*
|
||||||
* @param {Object=} options
|
* @param {Object=} options Object of option names and values
|
||||||
* @param {Function=} ready
|
* @param {Function=} ready Ready callback function
|
||||||
* @constructor
|
* @extends Tech
|
||||||
|
* @class Html5
|
||||||
*/
|
*/
|
||||||
class Html5 extends Tech {
|
class Html5 extends Tech {
|
||||||
|
|
||||||
@ -78,12 +80,22 @@ class Html5 extends Tech {
|
|||||||
this.triggerReady();
|
this.triggerReady();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Dispose of html5 media element
|
||||||
|
*
|
||||||
|
* @method dispose
|
||||||
|
*/
|
||||||
dispose() {
|
dispose() {
|
||||||
Html5.disposeMediaElement(this.el_);
|
Html5.disposeMediaElement(this.el_);
|
||||||
super.dispose();
|
super.dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
let el = this.options_.tag;
|
let el = this.options_.tag;
|
||||||
|
|
||||||
@ -147,6 +159,11 @@ class Html5 extends Tech {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Hide captions from text track
|
||||||
|
*
|
||||||
|
* @method hideCaptions
|
||||||
|
*/
|
||||||
hideCaptions() {
|
hideCaptions() {
|
||||||
let tracks = this.el_.querySelectorAll('track');
|
let tracks = this.el_.querySelectorAll('track');
|
||||||
let i = tracks.length;
|
let i = tracks.length;
|
||||||
@ -164,11 +181,42 @@ class Html5 extends Tech {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Play for html5 tech
|
||||||
|
*
|
||||||
|
* @method play
|
||||||
|
*/
|
||||||
play() { this.el_.play(); }
|
play() { this.el_.play(); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pause for html5 tech
|
||||||
|
*
|
||||||
|
* @method pause
|
||||||
|
*/
|
||||||
pause() { this.el_.pause(); }
|
pause() { this.el_.pause(); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Paused for html5 tech
|
||||||
|
*
|
||||||
|
* @return {Boolean}
|
||||||
|
* @method paused
|
||||||
|
*/
|
||||||
paused() { return this.el_.paused; }
|
paused() { return this.el_.paused; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get current time
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method currentTime
|
||||||
|
*/
|
||||||
currentTime() { return this.el_.currentTime; }
|
currentTime() { return this.el_.currentTime; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set current time
|
||||||
|
*
|
||||||
|
* @param {Number} seconds Current time of video
|
||||||
|
* @method setCurrentTime
|
||||||
|
*/
|
||||||
setCurrentTime(seconds) {
|
setCurrentTime(seconds) {
|
||||||
try {
|
try {
|
||||||
this.el_.currentTime = seconds;
|
this.el_.currentTime = seconds;
|
||||||
@ -178,19 +226,78 @@ class Html5 extends Tech {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get duration
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method duration
|
||||||
|
*/
|
||||||
duration() { return this.el_.duration || 0; }
|
duration() { return this.el_.duration || 0; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get a TimeRange object that represents the intersection
|
||||||
|
* of the time ranges for which the user agent has all
|
||||||
|
* relevant media
|
||||||
|
*
|
||||||
|
* @return {TimeRangeObject}
|
||||||
|
* @method buffered
|
||||||
|
*/
|
||||||
buffered() { return this.el_.buffered; }
|
buffered() { return this.el_.buffered; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get volume level
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method volume
|
||||||
|
*/
|
||||||
volume() { return this.el_.volume; }
|
volume() { return this.el_.volume; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set volume level
|
||||||
|
*
|
||||||
|
* @param {Number} percentAsDecimal Volume percent as a decimal
|
||||||
|
* @method setVolume
|
||||||
|
*/
|
||||||
setVolume(percentAsDecimal) { this.el_.volume = percentAsDecimal; }
|
setVolume(percentAsDecimal) { this.el_.volume = percentAsDecimal; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get if muted
|
||||||
|
*
|
||||||
|
* @return {Boolean}
|
||||||
|
* @method muted
|
||||||
|
*/
|
||||||
muted() { return this.el_.muted; }
|
muted() { return this.el_.muted; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set muted
|
||||||
|
*
|
||||||
|
* @param {Boolean} If player is to be muted or note
|
||||||
|
* @method setMuted
|
||||||
|
*/
|
||||||
setMuted(muted) { this.el_.muted = muted; }
|
setMuted(muted) { this.el_.muted = muted; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get player width
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method width
|
||||||
|
*/
|
||||||
width() { return this.el_.offsetWidth; }
|
width() { return this.el_.offsetWidth; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get player height
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method height
|
||||||
|
*/
|
||||||
height() { return this.el_.offsetHeight; }
|
height() { return this.el_.offsetHeight; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get if there is fullscreen support
|
||||||
|
*
|
||||||
|
* @return {Boolean}
|
||||||
|
* @method supportsFullScreen
|
||||||
|
*/
|
||||||
supportsFullScreen() {
|
supportsFullScreen() {
|
||||||
if (typeof this.el_.webkitEnterFullScreen === 'function') {
|
if (typeof this.el_.webkitEnterFullScreen === 'function') {
|
||||||
let userAgent = window.navigator.userAgent;
|
let userAgent = window.navigator.userAgent;
|
||||||
@ -202,6 +309,11 @@ class Html5 extends Tech {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Request to enter fullscreen
|
||||||
|
*
|
||||||
|
* @method enterFullScreen
|
||||||
|
*/
|
||||||
enterFullScreen() {
|
enterFullScreen() {
|
||||||
var video = this.el_;
|
var video = this.el_;
|
||||||
|
|
||||||
@ -231,10 +343,22 @@ class Html5 extends Tech {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Request to exit fullscreen
|
||||||
|
*
|
||||||
|
* @method exitFullScreen
|
||||||
|
*/
|
||||||
exitFullScreen() {
|
exitFullScreen() {
|
||||||
this.el_.webkitExitFullScreen();
|
this.el_.webkitExitFullScreen();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get/set video
|
||||||
|
*
|
||||||
|
* @param {Object=} src Source object
|
||||||
|
* @return {Object}
|
||||||
|
* @method src
|
||||||
|
*/
|
||||||
src(src) {
|
src(src) {
|
||||||
if (src === undefined) {
|
if (src === undefined) {
|
||||||
return this.el_.src;
|
return this.el_.src;
|
||||||
@ -244,42 +368,220 @@ class Html5 extends Tech {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set video
|
||||||
|
*
|
||||||
|
* @param {Object} src Source object
|
||||||
|
* @deprecated
|
||||||
|
* @method setSrc
|
||||||
|
*/
|
||||||
setSrc(src) { this.el_.src = src; }
|
setSrc(src) { this.el_.src = src; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Load media into player
|
||||||
|
*
|
||||||
|
* @method load
|
||||||
|
*/
|
||||||
load(){ this.el_.load(); }
|
load(){ this.el_.load(); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get current source
|
||||||
|
*
|
||||||
|
* @return {Object}
|
||||||
|
* @method currentSrc
|
||||||
|
*/
|
||||||
currentSrc() { return this.el_.currentSrc; }
|
currentSrc() { return this.el_.currentSrc; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get poster
|
||||||
|
*
|
||||||
|
* @return {String}
|
||||||
|
* @method poster
|
||||||
|
*/
|
||||||
poster() { return this.el_.poster; }
|
poster() { return this.el_.poster; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set poster
|
||||||
|
*
|
||||||
|
* @param {String} val URL to poster image
|
||||||
|
* @method
|
||||||
|
*/
|
||||||
setPoster(val) { this.el_.poster = val; }
|
setPoster(val) { this.el_.poster = val; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get preload attribute
|
||||||
|
*
|
||||||
|
* @return {String}
|
||||||
|
* @method preload
|
||||||
|
*/
|
||||||
preload() { return this.el_.preload; }
|
preload() { return this.el_.preload; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set preload attribute
|
||||||
|
*
|
||||||
|
* @param {String} val Value for preload attribute
|
||||||
|
* @method setPreload
|
||||||
|
*/
|
||||||
setPreload(val) { this.el_.preload = val; }
|
setPreload(val) { this.el_.preload = val; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get autoplay attribute
|
||||||
|
*
|
||||||
|
* @return {String}
|
||||||
|
* @method autoplay
|
||||||
|
*/
|
||||||
autoplay() { return this.el_.autoplay; }
|
autoplay() { return this.el_.autoplay; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set autoplay attribute
|
||||||
|
*
|
||||||
|
* @param {String} val Value for preload attribute
|
||||||
|
* @method setAutoplay
|
||||||
|
*/
|
||||||
setAutoplay(val) { this.el_.autoplay = val; }
|
setAutoplay(val) { this.el_.autoplay = val; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get controls attribute
|
||||||
|
*
|
||||||
|
* @return {String}
|
||||||
|
* @method controls
|
||||||
|
*/
|
||||||
controls() { return this.el_.controls; }
|
controls() { return this.el_.controls; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set controls attribute
|
||||||
|
*
|
||||||
|
* @param {String} val Value for controls attribute
|
||||||
|
* @method setControls
|
||||||
|
*/
|
||||||
setControls(val) { this.el_.controls = !!val; }
|
setControls(val) { this.el_.controls = !!val; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get loop attribute
|
||||||
|
*
|
||||||
|
* @return {String}
|
||||||
|
* @method loop
|
||||||
|
*/
|
||||||
loop() { return this.el_.loop; }
|
loop() { return this.el_.loop; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set loop attribute
|
||||||
|
*
|
||||||
|
* @param {String} val Value for loop attribute
|
||||||
|
* @method setLoop
|
||||||
|
*/
|
||||||
setLoop(val) { this.el_.loop = val; }
|
setLoop(val) { this.el_.loop = val; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get error value
|
||||||
|
*
|
||||||
|
* @return {String}
|
||||||
|
* @method error
|
||||||
|
*/
|
||||||
error() { return this.el_.error; }
|
error() { return this.el_.error; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get whether or not the player is in the "seeking" state
|
||||||
|
*
|
||||||
|
* @return {Boolean}
|
||||||
|
* @method seeking
|
||||||
|
*/
|
||||||
seeking() { return this.el_.seeking; }
|
seeking() { return this.el_.seeking; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get a TimeRanges object that represents the
|
||||||
|
* ranges of the media resource to which it is possible
|
||||||
|
* for the user agent to seek.
|
||||||
|
*
|
||||||
|
* @return {TimeRangeObject}
|
||||||
|
* @method seekable
|
||||||
|
*/
|
||||||
seekable() { return this.el_.seekable; }
|
seekable() { return this.el_.seekable; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get if video ended
|
||||||
|
*
|
||||||
|
* @return {Boolean}
|
||||||
|
* @method ended
|
||||||
|
*/
|
||||||
ended() { return this.el_.ended; }
|
ended() { return this.el_.ended; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the value of the muted content attribute
|
||||||
|
* This attribute has no dynamic effect, it only
|
||||||
|
* controls the default state of the element
|
||||||
|
*
|
||||||
|
* @return {Boolean}
|
||||||
|
* @method defaultMuted
|
||||||
|
*/
|
||||||
defaultMuted() { return this.el_.defaultMuted; }
|
defaultMuted() { return this.el_.defaultMuted; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get desired speed at which the media resource is to play
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method playbackRate
|
||||||
|
*/
|
||||||
playbackRate() { return this.el_.playbackRate; }
|
playbackRate() { return this.el_.playbackRate; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set desired speed at which the media resource is to play
|
||||||
|
*
|
||||||
|
* @param {Number} val Speed at which the media resource is to play
|
||||||
|
* @method setPlaybackRate
|
||||||
|
*/
|
||||||
setPlaybackRate(val) { this.el_.playbackRate = val; }
|
setPlaybackRate(val) { this.el_.playbackRate = val; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the current state of network activity for the element, from
|
||||||
|
* the list below
|
||||||
|
* NETWORK_EMPTY (numeric value 0)
|
||||||
|
* NETWORK_IDLE (numeric value 1)
|
||||||
|
* NETWORK_LOADING (numeric value 2)
|
||||||
|
* NETWORK_NO_SOURCE (numeric value 3)
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method networkState
|
||||||
|
*/
|
||||||
networkState() { return this.el_.networkState; }
|
networkState() { return this.el_.networkState; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get a value that expresses the current state of the element
|
||||||
|
* with respect to rendering the current playback position, from
|
||||||
|
* the codes in the list below
|
||||||
|
* HAVE_NOTHING (numeric value 0)
|
||||||
|
* HAVE_METADATA (numeric value 1)
|
||||||
|
* HAVE_CURRENT_DATA (numeric value 2)
|
||||||
|
* HAVE_FUTURE_DATA (numeric value 3)
|
||||||
|
* HAVE_ENOUGH_DATA (numeric value 4)
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method readyState
|
||||||
|
*/
|
||||||
readyState() { return this.el_.readyState; }
|
readyState() { return this.el_.readyState; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get width of video
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method videoWidth
|
||||||
|
*/
|
||||||
videoWidth() { return this.el_.videoWidth; }
|
videoWidth() { return this.el_.videoWidth; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get height of video
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method videoHeight
|
||||||
|
*/
|
||||||
videoHeight() { return this.el_.videoHeight; }
|
videoHeight() { return this.el_.videoHeight; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get text tracks
|
||||||
|
*
|
||||||
|
* @return {TextTrackList}
|
||||||
|
* @method textTracks
|
||||||
|
*/
|
||||||
textTracks() {
|
textTracks() {
|
||||||
if (!this['featuresNativeTextTracks']) {
|
if (!this['featuresNativeTextTracks']) {
|
||||||
return super.textTracks();
|
return super.textTracks();
|
||||||
@ -287,6 +589,17 @@ class Html5 extends Tech {
|
|||||||
|
|
||||||
return this.el_.textTracks;
|
return this.el_.textTracks;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates and returns a text track object
|
||||||
|
*
|
||||||
|
* @param {String} kind Text track kind (subtitles, captions, descriptions
|
||||||
|
* chapters and metadata)
|
||||||
|
* @param {String=} label Label to identify the text track
|
||||||
|
* @param {String=} language Two letter language abbreviation
|
||||||
|
* @return {TextTrackObject}
|
||||||
|
* @method addTextTrack
|
||||||
|
*/
|
||||||
addTextTrack(kind, label, language) {
|
addTextTrack(kind, label, language) {
|
||||||
if (!this['featuresNativeTextTracks']) {
|
if (!this['featuresNativeTextTracks']) {
|
||||||
return super.addTextTrack(kind, label, language);
|
return super.addTextTrack(kind, label, language);
|
||||||
@ -295,6 +608,14 @@ class Html5 extends Tech {
|
|||||||
return this.el_.addTextTrack(kind, label, language);
|
return this.el_.addTextTrack(kind, label, language);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates and returns a remote text track object
|
||||||
|
*
|
||||||
|
* @param {Object} options The object should contain values for
|
||||||
|
* kind, language, label and src (location of the WebVTT file)
|
||||||
|
* @return {TextTrackObject}
|
||||||
|
* @method addRemoteTextTrack
|
||||||
|
*/
|
||||||
addRemoteTextTrack(options={}) {
|
addRemoteTextTrack(options={}) {
|
||||||
if (!this['featuresNativeTextTracks']) {
|
if (!this['featuresNativeTextTracks']) {
|
||||||
return super.addRemoteTextTrack(options);
|
return super.addRemoteTextTrack(options);
|
||||||
@ -346,6 +667,12 @@ class Html5 extends Tech {
|
|||||||
return track;
|
return track;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Remove remote text track from TextTrackList object
|
||||||
|
*
|
||||||
|
* @param {TextTrackObject} track Texttrack object to remove
|
||||||
|
* @method removeRemoteTextTrack
|
||||||
|
*/
|
||||||
removeRemoteTextTrack(track) {
|
removeRemoteTextTrack(track) {
|
||||||
if (!this['featuresNativeTextTracks']) {
|
if (!this['featuresNativeTextTracks']) {
|
||||||
return super.removeRemoteTextTrack(track);
|
return super.removeRemoteTextTrack(track);
|
||||||
@ -370,12 +697,13 @@ class Html5 extends Tech {
|
|||||||
|
|
||||||
/* HTML5 Support Testing ---------------------------------------------------- */
|
/* HTML5 Support Testing ---------------------------------------------------- */
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Element for testing browser HTML5 video capabilities
|
* Element for testing browser HTML5 video capabilities
|
||||||
* @type {Element}
|
*
|
||||||
* @constant
|
* @type {Element}
|
||||||
* @private
|
* @constant
|
||||||
*/
|
* @private
|
||||||
|
*/
|
||||||
Html5.TEST_VID = document.createElement('video');
|
Html5.TEST_VID = document.createElement('video');
|
||||||
let track = document.createElement('track');
|
let track = document.createElement('track');
|
||||||
track.kind = 'captions';
|
track.kind = 'captions';
|
||||||
@ -383,8 +711,9 @@ track.srclang = 'en';
|
|||||||
track.label = 'English';
|
track.label = 'English';
|
||||||
Html5.TEST_VID.appendChild(track);
|
Html5.TEST_VID.appendChild(track);
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Check if HTML5 video is supported by this browser/device
|
* Check if HTML5 video is supported by this browser/device
|
||||||
|
*
|
||||||
* @return {Boolean}
|
* @return {Boolean}
|
||||||
*/
|
*/
|
||||||
Html5.isSupported = function(){
|
Html5.isSupported = function(){
|
||||||
@ -401,16 +730,18 @@ Html5.isSupported = function(){
|
|||||||
// Add Source Handler pattern functions to this tech
|
// Add Source Handler pattern functions to this tech
|
||||||
Tech.withSourceHandlers(Html5);
|
Tech.withSourceHandlers(Html5);
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* The default native source handler.
|
* The default native source handler.
|
||||||
* This simply passes the source to the video element. Nothing fancy.
|
* This simply passes the source to the video element. Nothing fancy.
|
||||||
|
*
|
||||||
* @param {Object} source The source object
|
* @param {Object} source The source object
|
||||||
* @param {Html5} tech The instance of the HTML5 tech
|
* @param {Html5} tech The instance of the HTML5 tech
|
||||||
*/
|
*/
|
||||||
Html5.nativeSourceHandler = {};
|
Html5.nativeSourceHandler = {};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Check if the video element can handle the source natively
|
* Check if the video element can handle the source natively
|
||||||
|
*
|
||||||
* @param {Object} source The source object
|
* @param {Object} source The source object
|
||||||
* @return {String} 'probably', 'maybe', or '' (empty string)
|
* @return {String} 'probably', 'maybe', or '' (empty string)
|
||||||
*/
|
*/
|
||||||
@ -440,10 +771,11 @@ Html5.nativeSourceHandler.canHandleSource = function(source){
|
|||||||
return '';
|
return '';
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Pass the source to the video element
|
* Pass the source to the video element
|
||||||
* Adaptive source handlers will have more complicated workflows before passing
|
* Adaptive source handlers will have more complicated workflows before passing
|
||||||
* video data to the video element
|
* video data to the video element
|
||||||
|
*
|
||||||
* @param {Object} source The source object
|
* @param {Object} source The source object
|
||||||
* @param {Html5} tech The instance of the Html5 tech
|
* @param {Html5} tech The instance of the Html5 tech
|
||||||
*/
|
*/
|
||||||
@ -451,19 +783,20 @@ Html5.nativeSourceHandler.handleSource = function(source, tech){
|
|||||||
tech.setSrc(source.src);
|
tech.setSrc(source.src);
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Clean up the source handler when disposing the player or switching sources..
|
* Clean up the source handler when disposing the player or switching sources..
|
||||||
* (no cleanup is needed when supporting the format natively)
|
* (no cleanup is needed when supporting the format natively)
|
||||||
*/
|
*/
|
||||||
Html5.nativeSourceHandler.dispose = function(){};
|
Html5.nativeSourceHandler.dispose = function(){};
|
||||||
|
|
||||||
// Register the native source handler
|
// Register the native source handler
|
||||||
Html5.registerSourceHandler(Html5.nativeSourceHandler);
|
Html5.registerSourceHandler(Html5.nativeSourceHandler);
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Check if the volume can be changed in this browser/device.
|
* Check if the volume can be changed in this browser/device.
|
||||||
* Volume cannot be changed in a lot of mobile devices.
|
* Volume cannot be changed in a lot of mobile devices.
|
||||||
* Specifically, it can't be changed from 1 on iOS.
|
* Specifically, it can't be changed from 1 on iOS.
|
||||||
|
*
|
||||||
* @return {Boolean}
|
* @return {Boolean}
|
||||||
*/
|
*/
|
||||||
Html5.canControlVolume = function(){
|
Html5.canControlVolume = function(){
|
||||||
@ -472,9 +805,10 @@ Html5.canControlVolume = function(){
|
|||||||
return volume !== Html5.TEST_VID.volume;
|
return volume !== Html5.TEST_VID.volume;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Check if playbackRate is supported in this browser/device.
|
* Check if playbackRate is supported in this browser/device.
|
||||||
* @return {[type]} [description]
|
*
|
||||||
|
* @return {Number} [description]
|
||||||
*/
|
*/
|
||||||
Html5.canControlPlaybackRate = function(){
|
Html5.canControlPlaybackRate = function(){
|
||||||
var playbackRate = Html5.TEST_VID.playbackRate;
|
var playbackRate = Html5.TEST_VID.playbackRate;
|
||||||
@ -482,8 +816,9 @@ Html5.canControlPlaybackRate = function(){
|
|||||||
return playbackRate !== Html5.TEST_VID.playbackRate;
|
return playbackRate !== Html5.TEST_VID.playbackRate;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Check to see if native text tracks are supported by this browser/device
|
* Check to see if native text tracks are supported by this browser/device
|
||||||
|
*
|
||||||
* @return {Boolean}
|
* @return {Boolean}
|
||||||
*/
|
*/
|
||||||
Html5.supportsNativeTextTracks = function() {
|
Html5.supportsNativeTextTracks = function() {
|
||||||
@ -505,40 +840,44 @@ Html5.supportsNativeTextTracks = function() {
|
|||||||
return supportsTextTracks;
|
return supportsTextTracks;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Set the tech's volume control support status
|
* Set the tech's volume control support status
|
||||||
|
*
|
||||||
* @type {Boolean}
|
* @type {Boolean}
|
||||||
*/
|
*/
|
||||||
Html5.prototype['featuresVolumeControl'] = Html5.canControlVolume();
|
Html5.prototype['featuresVolumeControl'] = Html5.canControlVolume();
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Set the tech's playbackRate support status
|
* Set the tech's playbackRate support status
|
||||||
|
*
|
||||||
* @type {Boolean}
|
* @type {Boolean}
|
||||||
*/
|
*/
|
||||||
Html5.prototype['featuresPlaybackRate'] = Html5.canControlPlaybackRate();
|
Html5.prototype['featuresPlaybackRate'] = Html5.canControlPlaybackRate();
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Set the tech's status on moving the video element.
|
* Set the tech's status on moving the video element.
|
||||||
* In iOS, if you move a video element in the DOM, it breaks video playback.
|
* In iOS, if you move a video element in the DOM, it breaks video playback.
|
||||||
|
*
|
||||||
* @type {Boolean}
|
* @type {Boolean}
|
||||||
*/
|
*/
|
||||||
Html5.prototype['movingMediaElementInDOM'] = !browser.IS_IOS;
|
Html5.prototype['movingMediaElementInDOM'] = !browser.IS_IOS;
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Set the the tech's fullscreen resize support status.
|
* Set the the tech's fullscreen resize support status.
|
||||||
* HTML video is able to automatically resize when going to fullscreen.
|
* HTML video is able to automatically resize when going to fullscreen.
|
||||||
* (No longer appears to be used. Can probably be removed.)
|
* (No longer appears to be used. Can probably be removed.)
|
||||||
*/
|
*/
|
||||||
Html5.prototype['featuresFullscreenResize'] = true;
|
Html5.prototype['featuresFullscreenResize'] = true;
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Set the tech's progress event support status
|
* Set the tech's progress event support status
|
||||||
* (this disables the manual progress events of the Tech)
|
* (this disables the manual progress events of the Tech)
|
||||||
*/
|
*/
|
||||||
Html5.prototype['featuresProgressEvents'] = true;
|
Html5.prototype['featuresProgressEvents'] = true;
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Sets the tech's status on native text track support
|
* Sets the tech's status on native text track support
|
||||||
|
*
|
||||||
* @type {Boolean}
|
* @type {Boolean}
|
||||||
*/
|
*/
|
||||||
Html5.prototype['featuresNativeTextTracks'] = Html5.supportsNativeTextTracks();
|
Html5.prototype['featuresNativeTextTracks'] = Html5.supportsNativeTextTracks();
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file loader.js
|
||||||
|
*/
|
||||||
import Component from '../component';
|
import Component from '../component';
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
import toTitleCase from '../utils/to-title-case.js';
|
import toTitleCase from '../utils/to-title-case.js';
|
||||||
@ -6,7 +9,11 @@ import toTitleCase from '../utils/to-title-case.js';
|
|||||||
* The Media Loader is the component that decides which playback technology to load
|
* The Media Loader is the component that decides which playback technology to load
|
||||||
* when the player is initialized.
|
* when the player is initialized.
|
||||||
*
|
*
|
||||||
* @constructor
|
* @param {Object} player Main Player
|
||||||
|
* @param {Object=} options Object of option names and values
|
||||||
|
* @param {Function=} ready Ready callback function
|
||||||
|
* @extends Component
|
||||||
|
* @class MediaLoader
|
||||||
*/
|
*/
|
||||||
class MediaLoader extends Component {
|
class MediaLoader extends Component {
|
||||||
|
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
/**
|
/**
|
||||||
* @fileoverview Media Technology Controller - Base class for media playback
|
* @file tech.js
|
||||||
|
* Media Technology Controller - Base class for media playback
|
||||||
* technology controllers like Flash and HTML5
|
* technology controllers like Flash and HTML5
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -15,9 +16,11 @@ import document from 'global/document';
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Base class for media (HTML5 Video, Flash) controllers
|
* Base class for media (HTML5 Video, Flash) controllers
|
||||||
* @param {Player|Object} player Central player instance
|
*
|
||||||
* @param {Object=} options Options object
|
* @param {Object=} options Options object
|
||||||
* @constructor
|
* @param {Function=} ready Ready callback function
|
||||||
|
* @extends Component
|
||||||
|
* @class Tech
|
||||||
*/
|
*/
|
||||||
class Tech extends Component {
|
class Tech extends Component {
|
||||||
|
|
||||||
@ -61,19 +64,18 @@ class Tech extends Component {
|
|||||||
* on a mobile device a click on the video toggles controls.
|
* on a mobile device a click on the video toggles controls.
|
||||||
* (toggling controls is done by toggling the user state between active and
|
* (toggling controls is done by toggling the user state between active and
|
||||||
* inactive)
|
* inactive)
|
||||||
*
|
|
||||||
* A tap can signal that a user has become active, or has become inactive
|
* A tap can signal that a user has become active, or has become inactive
|
||||||
* e.g. a quick tap on an iPhone movie should reveal the controls. Another
|
* e.g. a quick tap on an iPhone movie should reveal the controls. Another
|
||||||
* quick tap should hide them again (signaling the user is in an inactive
|
* quick tap should hide them again (signaling the user is in an inactive
|
||||||
* viewing state)
|
* viewing state)
|
||||||
*
|
|
||||||
* In addition to this, we still want the user to be considered inactive after
|
* In addition to this, we still want the user to be considered inactive after
|
||||||
* a few seconds of inactivity.
|
* a few seconds of inactivity.
|
||||||
*
|
|
||||||
* Note: the only part of iOS interaction we can't mimic with this setup
|
* Note: the only part of iOS interaction we can't mimic with this setup
|
||||||
* is a touch and hold on the video element counting as activity in order to
|
* is a touch and hold on the video element counting as activity in order to
|
||||||
* keep the controls showing, but that shouldn't be an issue. A touch and hold on
|
* keep the controls showing, but that shouldn't be an issue. A touch and hold on
|
||||||
* any controls will still keep the user active
|
* any controls will still keep the user active
|
||||||
|
*
|
||||||
|
* @method initControlsListeners
|
||||||
*/
|
*/
|
||||||
initControlsListeners() {
|
initControlsListeners() {
|
||||||
// if we're loading the playback object after it has started loading or playing the
|
// if we're loading the playback object after it has started loading or playing the
|
||||||
@ -92,6 +94,11 @@ class Tech extends Component {
|
|||||||
================================================================================ */
|
================================================================================ */
|
||||||
// Manually trigger progress events based on changes to the buffered amount
|
// Manually trigger progress events based on changes to the buffered amount
|
||||||
// Many flash players and older HTML5 browsers don't send progress or progress-like events
|
// Many flash players and older HTML5 browsers don't send progress or progress-like events
|
||||||
|
/**
|
||||||
|
* Turn on progress events
|
||||||
|
*
|
||||||
|
* @method manualProgressOn
|
||||||
|
*/
|
||||||
manualProgressOn() {
|
manualProgressOn() {
|
||||||
this.on('durationchange', this.onDurationChange);
|
this.on('durationchange', this.onDurationChange);
|
||||||
|
|
||||||
@ -101,6 +108,11 @@ class Tech extends Component {
|
|||||||
this.trackProgress();
|
this.trackProgress();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Turn off progress events
|
||||||
|
*
|
||||||
|
* @method manualProgressOff
|
||||||
|
*/
|
||||||
manualProgressOff() {
|
manualProgressOff() {
|
||||||
this.manualProgress = false;
|
this.manualProgress = false;
|
||||||
this.stopTrackingProgress();
|
this.stopTrackingProgress();
|
||||||
@ -108,6 +120,11 @@ class Tech extends Component {
|
|||||||
this.off('durationchange', this.onDurationChange);
|
this.off('durationchange', this.onDurationChange);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Track progress
|
||||||
|
*
|
||||||
|
* @method trackProgress
|
||||||
|
*/
|
||||||
trackProgress() {
|
trackProgress() {
|
||||||
this.progressInterval = this.setInterval(Fn.bind(this, function(){
|
this.progressInterval = this.setInterval(Fn.bind(this, function(){
|
||||||
// Don't trigger unless buffered amount is greater than last time
|
// Don't trigger unless buffered amount is greater than last time
|
||||||
@ -126,23 +143,50 @@ class Tech extends Component {
|
|||||||
}), 500);
|
}), 500);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update duration
|
||||||
|
*
|
||||||
|
* @method onDurationChange
|
||||||
|
*/
|
||||||
onDurationChange() {
|
onDurationChange() {
|
||||||
this.duration_ = this.duration();
|
this.duration_ = this.duration();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create and get TimeRange object for buffering
|
||||||
|
*
|
||||||
|
* @return {TimeRangeObject}
|
||||||
|
* @method buffered
|
||||||
|
*/
|
||||||
buffered() {
|
buffered() {
|
||||||
return createTimeRange(0, 0);
|
return createTimeRange(0, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get buffered percent
|
||||||
|
*
|
||||||
|
* @return {Number}
|
||||||
|
* @method bufferedPercent
|
||||||
|
*/
|
||||||
bufferedPercent() {
|
bufferedPercent() {
|
||||||
return bufferedPercent(this.buffered(), this.duration_);
|
return bufferedPercent(this.buffered(), this.duration_);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Stops tracking progress by clearing progress interval
|
||||||
|
*
|
||||||
|
* @method stopTrackingProgress
|
||||||
|
*/
|
||||||
stopTrackingProgress() {
|
stopTrackingProgress() {
|
||||||
this.clearInterval(this.progressInterval);
|
this.clearInterval(this.progressInterval);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*! Time Tracking -------------------------------------------------------------- */
|
/*! Time Tracking -------------------------------------------------------------- */
|
||||||
|
/**
|
||||||
|
* Set event listeners for on play and pause and tracking current time
|
||||||
|
*
|
||||||
|
* @method manualTimeUpdatesOn
|
||||||
|
*/
|
||||||
manualTimeUpdatesOn() {
|
manualTimeUpdatesOn() {
|
||||||
this.manualTimeUpdates = true;
|
this.manualTimeUpdates = true;
|
||||||
|
|
||||||
@ -150,6 +194,11 @@ class Tech extends Component {
|
|||||||
this.on('pause', this.stopTrackingCurrentTime);
|
this.on('pause', this.stopTrackingCurrentTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Remove event listeners for on play and pause and tracking current time
|
||||||
|
*
|
||||||
|
* @method manualTimeUpdatesOff
|
||||||
|
*/
|
||||||
manualTimeUpdatesOff() {
|
manualTimeUpdatesOff() {
|
||||||
this.manualTimeUpdates = false;
|
this.manualTimeUpdates = false;
|
||||||
this.stopTrackingCurrentTime();
|
this.stopTrackingCurrentTime();
|
||||||
@ -157,6 +206,11 @@ class Tech extends Component {
|
|||||||
this.off('pause', this.stopTrackingCurrentTime);
|
this.off('pause', this.stopTrackingCurrentTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Tracks current time
|
||||||
|
*
|
||||||
|
* @method trackCurrentTime
|
||||||
|
*/
|
||||||
trackCurrentTime() {
|
trackCurrentTime() {
|
||||||
if (this.currentTimeInterval) { this.stopTrackingCurrentTime(); }
|
if (this.currentTimeInterval) { this.stopTrackingCurrentTime(); }
|
||||||
this.currentTimeInterval = this.setInterval(function(){
|
this.currentTimeInterval = this.setInterval(function(){
|
||||||
@ -164,7 +218,11 @@ class Tech extends Component {
|
|||||||
}, 250); // 42 = 24 fps // 250 is what Webkit uses // FF uses 15
|
}, 250); // 42 = 24 fps // 250 is what Webkit uses // FF uses 15
|
||||||
}
|
}
|
||||||
|
|
||||||
// Turn off play progress tracking (when paused or dragging)
|
/**
|
||||||
|
* Turn off play progress tracking (when paused or dragging)
|
||||||
|
*
|
||||||
|
* @method stopTrackingCurrentTime
|
||||||
|
*/
|
||||||
stopTrackingCurrentTime() {
|
stopTrackingCurrentTime() {
|
||||||
this.clearInterval(this.currentTimeInterval);
|
this.clearInterval(this.currentTimeInterval);
|
||||||
|
|
||||||
@ -173,6 +231,11 @@ class Tech extends Component {
|
|||||||
this.trigger({ type: 'timeupdate', target: this, manuallyTriggered: true });
|
this.trigger({ type: 'timeupdate', target: this, manuallyTriggered: true });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Turn off any manual progress or timeupdate tracking
|
||||||
|
*
|
||||||
|
* @method dispose
|
||||||
|
*/
|
||||||
dispose() {
|
dispose() {
|
||||||
// Turn off any manual progress or timeupdate tracking
|
// Turn off any manual progress or timeupdate tracking
|
||||||
if (this.manualProgress) { this.manualProgressOff(); }
|
if (this.manualProgress) { this.manualProgressOff(); }
|
||||||
@ -182,11 +245,21 @@ class Tech extends Component {
|
|||||||
super.dispose();
|
super.dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set current time
|
||||||
|
*
|
||||||
|
* @method setCurrentTime
|
||||||
|
*/
|
||||||
setCurrentTime() {
|
setCurrentTime() {
|
||||||
// improve the accuracy of manual timeupdates
|
// improve the accuracy of manual timeupdates
|
||||||
if (this.manualTimeUpdates) { this.trigger({ type: 'timeupdate', target: this, manuallyTriggered: true }); }
|
if (this.manualTimeUpdates) { this.trigger({ type: 'timeupdate', target: this, manuallyTriggered: true }); }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Initialize texttrack listeners
|
||||||
|
*
|
||||||
|
* @method initTextTrackListeners
|
||||||
|
*/
|
||||||
initTextTrackListeners() {
|
initTextTrackListeners() {
|
||||||
let textTrackListChanges = Fn.bind(this, function() {
|
let textTrackListChanges = Fn.bind(this, function() {
|
||||||
this.trigger('texttrackchange');
|
this.trigger('texttrackchange');
|
||||||
@ -205,6 +278,11 @@ class Tech extends Component {
|
|||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Emulate texttracks
|
||||||
|
*
|
||||||
|
* @method emulateTextTracks
|
||||||
|
*/
|
||||||
emulateTextTracks() {
|
emulateTextTracks() {
|
||||||
if (!window['WebVTT'] && this.el().parentNode != null) {
|
if (!window['WebVTT'] && this.el().parentNode != null) {
|
||||||
let script = document.createElement('script');
|
let script = document.createElement('script');
|
||||||
@ -239,22 +317,44 @@ class Tech extends Component {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Provide default methods for text tracks.
|
* Provide default methods for text tracks.
|
||||||
*
|
*
|
||||||
* Html5 tech overrides these.
|
* Html5 tech overrides these.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get texttracks
|
||||||
|
*
|
||||||
|
* @returns {TextTrackList}
|
||||||
|
* @method textTracks
|
||||||
|
*/
|
||||||
textTracks() {
|
textTracks() {
|
||||||
this.textTracks_ = this.textTracks_ || new TextTrackList();
|
this.textTracks_ = this.textTracks_ || new TextTrackList();
|
||||||
return this.textTracks_;
|
return this.textTracks_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get remote texttracks
|
||||||
|
*
|
||||||
|
* @returns {TextTrackList}
|
||||||
|
* @method remoteTextTracks
|
||||||
|
*/
|
||||||
remoteTextTracks() {
|
remoteTextTracks() {
|
||||||
this.remoteTextTracks_ = this.remoteTextTracks_ || new TextTrackList();
|
this.remoteTextTracks_ = this.remoteTextTracks_ || new TextTrackList();
|
||||||
return this.remoteTextTracks_;
|
return this.remoteTextTracks_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates and returns a remote text track object
|
||||||
|
*
|
||||||
|
* @param {String} kind Text track kind (subtitles, captions, descriptions
|
||||||
|
* chapters and metadata)
|
||||||
|
* @param {String=} label Label to identify the text track
|
||||||
|
* @param {String=} language Two letter language abbreviation
|
||||||
|
* @return {TextTrackObject}
|
||||||
|
* @method addTextTrack
|
||||||
|
*/
|
||||||
addTextTrack(kind, label, language) {
|
addTextTrack(kind, label, language) {
|
||||||
if (!kind) {
|
if (!kind) {
|
||||||
throw new Error('TextTrack kind is required but was not provided');
|
throw new Error('TextTrack kind is required but was not provided');
|
||||||
@ -263,6 +363,14 @@ class Tech extends Component {
|
|||||||
return createTrackHelper(this, kind, label, language);
|
return createTrackHelper(this, kind, label, language);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates and returns a remote text track object
|
||||||
|
*
|
||||||
|
* @param {Object} options The object should contain values for
|
||||||
|
* kind, language, label and src (location of the WebVTT file)
|
||||||
|
* @return {TextTrackObject}
|
||||||
|
* @method addRemoteTextTrack
|
||||||
|
*/
|
||||||
addRemoteTextTrack(options) {
|
addRemoteTextTrack(options) {
|
||||||
let track = createTrackHelper(this, options.kind, options.label, options.language, options);
|
let track = createTrackHelper(this, options.kind, options.label, options.language, options);
|
||||||
this.remoteTextTracks().addTrack_(track);
|
this.remoteTextTracks().addTrack_(track);
|
||||||
@ -271,6 +379,12 @@ class Tech extends Component {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Remove remote texttrack
|
||||||
|
*
|
||||||
|
* @param {TextTrackObject} track Texttrack to remove
|
||||||
|
* @method removeRemoteTextTrack
|
||||||
|
*/
|
||||||
removeRemoteTextTrack(track) {
|
removeRemoteTextTrack(track) {
|
||||||
this.textTracks().removeTrack_(track);
|
this.textTracks().removeTrack_(track);
|
||||||
this.remoteTextTracks().removeTrack_(track);
|
this.remoteTextTracks().removeTrack_(track);
|
||||||
@ -278,16 +392,18 @@ class Tech extends Component {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Provide a default setPoster method for techs
|
* Provide a default setPoster method for techs
|
||||||
*
|
|
||||||
* Poster support for techs should be optional, so we don't want techs to
|
* Poster support for techs should be optional, so we don't want techs to
|
||||||
* break if they don't have a way to set a poster.
|
* break if they don't have a way to set a poster.
|
||||||
|
*
|
||||||
|
* @method setPoster
|
||||||
*/
|
*/
|
||||||
setPoster() {}
|
setPoster() {}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* List of associated text tracks
|
* List of associated text tracks
|
||||||
|
*
|
||||||
* @type {Array}
|
* @type {Array}
|
||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
@ -325,8 +441,8 @@ Tech.prototype.featuresTimeupdateEvents = false;
|
|||||||
|
|
||||||
Tech.prototype.featuresNativeTextTracks = false;
|
Tech.prototype.featuresNativeTextTracks = false;
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* A functional mixin for techs that want to use the Source Handler pattern.
|
* A functional mixin for techs that want to use the Source Handler pattern.
|
||||||
*
|
*
|
||||||
* ##### EXAMPLE:
|
* ##### EXAMPLE:
|
||||||
*
|
*
|
||||||
@ -334,14 +450,14 @@ Tech.prototype.featuresNativeTextTracks = false;
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
Tech.withSourceHandlers = function(_Tech){
|
Tech.withSourceHandlers = function(_Tech){
|
||||||
/**
|
/*
|
||||||
* Register a source handler
|
* Register a source handler
|
||||||
* Source handlers are scripts for handling specific formats.
|
* Source handlers are scripts for handling specific formats.
|
||||||
* The source handler pattern is used for adaptive formats (HLS, DASH) that
|
* The source handler pattern is used for adaptive formats (HLS, DASH) that
|
||||||
* manually load video data and feed it into a Source Buffer (Media Source Extensions)
|
* manually load video data and feed it into a Source Buffer (Media Source Extensions)
|
||||||
* @param {Function} handler The source handler
|
* @param {Function} handler The source handler
|
||||||
* @param {Boolean} first Register it before any existing handlers
|
* @param {Boolean} first Register it before any existing handlers
|
||||||
*/
|
*/
|
||||||
_Tech.registerSourceHandler = function(handler, index){
|
_Tech.registerSourceHandler = function(handler, index){
|
||||||
let handlers = _Tech.sourceHandlers;
|
let handlers = _Tech.sourceHandlers;
|
||||||
|
|
||||||
@ -357,13 +473,13 @@ Tech.withSourceHandlers = function(_Tech){
|
|||||||
handlers.splice(index, 0, handler);
|
handlers.splice(index, 0, handler);
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Return the first source handler that supports the source
|
* Return the first source handler that supports the source
|
||||||
* TODO: Answer question: should 'probably' be prioritized over 'maybe'
|
* TODO: Answer question: should 'probably' be prioritized over 'maybe'
|
||||||
* @param {Object} source The source object
|
* @param {Object} source The source object
|
||||||
* @returns {Object} The first source handler that supports the source
|
* @returns {Object} The first source handler that supports the source
|
||||||
* @returns {null} Null if no source handler is found
|
* @returns {null} Null if no source handler is found
|
||||||
*/
|
*/
|
||||||
_Tech.selectSourceHandler = function(source){
|
_Tech.selectSourceHandler = function(source){
|
||||||
let handlers = _Tech.sourceHandlers || [];
|
let handlers = _Tech.sourceHandlers || [];
|
||||||
let can;
|
let can;
|
||||||
@ -379,11 +495,11 @@ Tech.withSourceHandlers = function(_Tech){
|
|||||||
return null;
|
return null;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Check if the tech can support the given source
|
* Check if the tech can support the given source
|
||||||
* @param {Object} srcObj The source object
|
* @param {Object} srcObj The source object
|
||||||
* @return {String} 'probably', 'maybe', or '' (empty string)
|
* @return {String} 'probably', 'maybe', or '' (empty string)
|
||||||
*/
|
*/
|
||||||
_Tech.canPlaySource = function(srcObj){
|
_Tech.canPlaySource = function(srcObj){
|
||||||
let sh = _Tech.selectSourceHandler(srcObj);
|
let sh = _Tech.selectSourceHandler(srcObj);
|
||||||
|
|
||||||
@ -394,13 +510,13 @@ Tech.withSourceHandlers = function(_Tech){
|
|||||||
return '';
|
return '';
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Create a function for setting the source using a source object
|
* Create a function for setting the source using a source object
|
||||||
* and source handlers.
|
* and source handlers.
|
||||||
* Should never be called unless a source handler was found.
|
* Should never be called unless a source handler was found.
|
||||||
* @param {Object} source A source object with src and type keys
|
* @param {Object} source A source object with src and type keys
|
||||||
* @return {Tech} self
|
* @return {Tech} self
|
||||||
*/
|
*/
|
||||||
_Tech.prototype.setSource = function(source){
|
_Tech.prototype.setSource = function(source){
|
||||||
let sh = _Tech.selectSourceHandler(source);
|
let sh = _Tech.selectSourceHandler(source);
|
||||||
|
|
||||||
@ -425,9 +541,9 @@ Tech.withSourceHandlers = function(_Tech){
|
|||||||
return this;
|
return this;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Clean up any existing source handler
|
* Clean up any existing source handler
|
||||||
*/
|
*/
|
||||||
_Tech.prototype.disposeSourceHandler = function(){
|
_Tech.prototype.disposeSourceHandler = function(){
|
||||||
if (this.sourceHandler_ && this.sourceHandler_.dispose) {
|
if (this.sourceHandler_ && this.sourceHandler_.dispose) {
|
||||||
this.sourceHandler_.dispose();
|
this.sourceHandler_.dispose();
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file text-track-cue-list.js
|
||||||
|
*/
|
||||||
import * as browser from '../utils/browser.js';
|
import * as browser from '../utils/browser.js';
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
|
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file text-track-display.js
|
||||||
|
*/
|
||||||
import Component from '../component';
|
import Component from '../component';
|
||||||
import Menu from '../menu/menu.js';
|
import Menu from '../menu/menu.js';
|
||||||
import MenuItem from '../menu/menu-item.js';
|
import MenuItem from '../menu/menu-item.js';
|
||||||
@ -24,7 +27,11 @@ const fontMap = {
|
|||||||
/**
|
/**
|
||||||
* The component for displaying text track cues
|
* The component for displaying text track cues
|
||||||
*
|
*
|
||||||
* @constructor
|
* @param {Object} player Main Player
|
||||||
|
* @param {Object=} options Object of option names and values
|
||||||
|
* @param {Function=} ready Ready callback function
|
||||||
|
* @extends Component
|
||||||
|
* @class TextTrackDisplay
|
||||||
*/
|
*/
|
||||||
class TextTrackDisplay extends Component {
|
class TextTrackDisplay extends Component {
|
||||||
|
|
||||||
@ -54,6 +61,11 @@ class TextTrackDisplay extends Component {
|
|||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Toggle display texttracks
|
||||||
|
*
|
||||||
|
* @method toggleDisplay
|
||||||
|
*/
|
||||||
toggleDisplay() {
|
toggleDisplay() {
|
||||||
if (this.player_.tech && this.player_.tech['featuresNativeTextTracks']) {
|
if (this.player_.tech && this.player_.tech['featuresNativeTextTracks']) {
|
||||||
this.hide();
|
this.hide();
|
||||||
@ -62,18 +74,34 @@ class TextTrackDisplay extends Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-text-track-display'
|
className: 'vjs-text-track-display'
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Clear display texttracks
|
||||||
|
*
|
||||||
|
* @method clearDisplay
|
||||||
|
*/
|
||||||
clearDisplay() {
|
clearDisplay() {
|
||||||
if (typeof window['WebVTT'] === 'function') {
|
if (typeof window['WebVTT'] === 'function') {
|
||||||
window['WebVTT']['processCues'](window, [], this.el_);
|
window['WebVTT']['processCues'](window, [], this.el_);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update display texttracks
|
||||||
|
*
|
||||||
|
* @method updateDisplay
|
||||||
|
*/
|
||||||
updateDisplay() {
|
updateDisplay() {
|
||||||
var tracks = this.player_.textTracks();
|
var tracks = this.player_.textTracks();
|
||||||
|
|
||||||
@ -91,6 +119,12 @@ class TextTrackDisplay extends Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add texttrack to texttrack list
|
||||||
|
*
|
||||||
|
* @param {TextTrackObject} track Texttrack object to be added to list
|
||||||
|
* @method updateForTrack
|
||||||
|
*/
|
||||||
updateForTrack(track) {
|
updateForTrack(track) {
|
||||||
if (typeof window['WebVTT'] !== 'function' || !track['activeCues']) {
|
if (typeof window['WebVTT'] !== 'function' || !track['activeCues']) {
|
||||||
return;
|
return;
|
||||||
@ -165,7 +199,14 @@ class TextTrackDisplay extends Component {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add cue HTML to display
|
/**
|
||||||
|
* Add cue HTML to display
|
||||||
|
*
|
||||||
|
* @param {Number} color Hex number for color, like #f0e
|
||||||
|
* @param {Number} opacity Value for opacity,0.0 - 1.0
|
||||||
|
* @return {RGBAColor} In the form 'rgba(255, 0, 0, 0.3)'
|
||||||
|
* @method constructColor
|
||||||
|
*/
|
||||||
function constructColor(color, opacity) {
|
function constructColor(color, opacity) {
|
||||||
return 'rgba(' +
|
return 'rgba(' +
|
||||||
// color looks like "#f0e"
|
// color looks like "#f0e"
|
||||||
@ -175,8 +216,17 @@ function constructColor(color, opacity) {
|
|||||||
opacity + ')';
|
opacity + ')';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Try to update style
|
||||||
|
* Some style changes will throw an error, particularly in IE8. Those should be noops.
|
||||||
|
*
|
||||||
|
* @param {Element} el The element to be styles
|
||||||
|
* @param {CSSProperty} style The CSS property to be styled
|
||||||
|
* @param {CSSStyle} rule The actual style to be applied to the property
|
||||||
|
* @method tryUpdateStyle
|
||||||
|
*/
|
||||||
function tryUpdateStyle(el, style, rule) {
|
function tryUpdateStyle(el, style, rule) {
|
||||||
// some style changes will throw an error, particularly in IE8. Those should be noops.
|
//
|
||||||
try {
|
try {
|
||||||
el.style[style] = rule;
|
el.style[style] = rule;
|
||||||
} catch (e) {}
|
} catch (e) {}
|
||||||
|
@ -1,4 +1,6 @@
|
|||||||
/*
|
/**
|
||||||
|
* @file text-track-enums.js
|
||||||
|
*
|
||||||
* https://html.spec.whatwg.org/multipage/embedded-content.html#texttrackmode
|
* https://html.spec.whatwg.org/multipage/embedded-content.html#texttrackmode
|
||||||
*
|
*
|
||||||
* enum TextTrackMode { "disabled", "hidden", "showing" };
|
* enum TextTrackMode { "disabled", "hidden", "showing" };
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file text-track-list.js
|
||||||
|
*/
|
||||||
import EventEmitter from '../event-emitter';
|
import EventEmitter from '../event-emitter';
|
||||||
import * as Fn from '../utils/fn.js';
|
import * as Fn from '../utils/fn.js';
|
||||||
import * as browser from '../utils/browser.js';
|
import * as browser from '../utils/browser.js';
|
||||||
@ -52,7 +55,7 @@ TextTrackList.prototype.constructor = TextTrackList;
|
|||||||
* change - One or more tracks in the track list have been enabled or disabled.
|
* change - One or more tracks in the track list have been enabled or disabled.
|
||||||
* addtrack - A track has been added to the track list.
|
* addtrack - A track has been added to the track list.
|
||||||
* removetrack - A track has been removed from the track list.
|
* removetrack - A track has been removed from the track list.
|
||||||
*/
|
*/
|
||||||
TextTrackList.prototype.allowedEvents_ = {
|
TextTrackList.prototype.allowedEvents_ = {
|
||||||
'change': 'change',
|
'change': 'change',
|
||||||
'addtrack': 'addtrack',
|
'addtrack': 'addtrack',
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file text-track-settings.js
|
||||||
|
*/
|
||||||
import Component from '../component';
|
import Component from '../component';
|
||||||
import * as Events from '../utils/events.js';
|
import * as Events from '../utils/events.js';
|
||||||
import * as Fn from '../utils/fn.js';
|
import * as Fn from '../utils/fn.js';
|
||||||
@ -5,6 +8,14 @@ import log from '../utils/log.js';
|
|||||||
import safeParseTuple from 'safe-json-parse/tuple';
|
import safeParseTuple from 'safe-json-parse/tuple';
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Manipulate settings of texttracks
|
||||||
|
*
|
||||||
|
* @param {Object} player Main Player
|
||||||
|
* @param {Object=} options Object of option names and values
|
||||||
|
* @extends Component
|
||||||
|
* @class TextTrackSettings
|
||||||
|
*/
|
||||||
class TextTrackSettings extends Component {
|
class TextTrackSettings extends Component {
|
||||||
|
|
||||||
constructor(player, options) {
|
constructor(player, options) {
|
||||||
@ -49,6 +60,12 @@ class TextTrackSettings extends Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the component's DOM element
|
||||||
|
*
|
||||||
|
* @return {Element}
|
||||||
|
* @method createEl
|
||||||
|
*/
|
||||||
createEl() {
|
createEl() {
|
||||||
return super.createEl('div', {
|
return super.createEl('div', {
|
||||||
className: 'vjs-caption-settings vjs-modal-overlay',
|
className: 'vjs-caption-settings vjs-modal-overlay',
|
||||||
@ -56,6 +73,21 @@ class TextTrackSettings extends Component {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get texttrack settings
|
||||||
|
* Settings are
|
||||||
|
* .vjs-edge-style
|
||||||
|
* .vjs-font-family
|
||||||
|
* .vjs-fg-color
|
||||||
|
* .vjs-text-opacity
|
||||||
|
* .vjs-bg-color
|
||||||
|
* .vjs-bg-opacity
|
||||||
|
* .window-color
|
||||||
|
* .vjs-window-opacity
|
||||||
|
*
|
||||||
|
* @return {Object}
|
||||||
|
* @method getValues
|
||||||
|
*/
|
||||||
getValues() {
|
getValues() {
|
||||||
const el = this.el();
|
const el = this.el();
|
||||||
|
|
||||||
@ -88,6 +120,21 @@ class TextTrackSettings extends Component {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set texttrack settings
|
||||||
|
* Settings are
|
||||||
|
* .vjs-edge-style
|
||||||
|
* .vjs-font-family
|
||||||
|
* .vjs-fg-color
|
||||||
|
* .vjs-text-opacity
|
||||||
|
* .vjs-bg-color
|
||||||
|
* .vjs-bg-opacity
|
||||||
|
* .window-color
|
||||||
|
* .vjs-window-opacity
|
||||||
|
*
|
||||||
|
* @param {Object} values Object with texttrack setting values
|
||||||
|
* @method setValues
|
||||||
|
*/
|
||||||
setValues(values) {
|
setValues(values) {
|
||||||
const el = this.el();
|
const el = this.el();
|
||||||
|
|
||||||
@ -109,6 +156,11 @@ class TextTrackSettings extends Component {
|
|||||||
setSelectedOption(el.querySelector('.vjs-font-percent > select'), fontPercent);
|
setSelectedOption(el.querySelector('.vjs-font-percent > select'), fontPercent);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Restore texttrack settings
|
||||||
|
*
|
||||||
|
* @method restoreSettings
|
||||||
|
*/
|
||||||
restoreSettings() {
|
restoreSettings() {
|
||||||
let [err, values] = safeParseTuple(window.localStorage.getItem('vjs-text-track-settings'));
|
let [err, values] = safeParseTuple(window.localStorage.getItem('vjs-text-track-settings'));
|
||||||
|
|
||||||
@ -121,6 +173,11 @@ class TextTrackSettings extends Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Save texttrack settings to local storage
|
||||||
|
*
|
||||||
|
* @method saveSettings
|
||||||
|
*/
|
||||||
saveSettings() {
|
saveSettings() {
|
||||||
if (!this.options_.persistTextTrackSettings) {
|
if (!this.options_.persistTextTrackSettings) {
|
||||||
return;
|
return;
|
||||||
@ -136,6 +193,11 @@ class TextTrackSettings extends Component {
|
|||||||
} catch (e) {}
|
} catch (e) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Update display of texttrack settings
|
||||||
|
*
|
||||||
|
* @method updateDisplay
|
||||||
|
*/
|
||||||
updateDisplay() {
|
updateDisplay() {
|
||||||
let ttDisplay = this.player_.getChild('textTrackDisplay');
|
let ttDisplay = this.player_.getChild('textTrackDisplay');
|
||||||
if (ttDisplay) {
|
if (ttDisplay) {
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file text-track.js
|
||||||
|
*/
|
||||||
import TextTrackCueList from './text-track-cue-list';
|
import TextTrackCueList from './text-track-cue-list';
|
||||||
import * as Fn from '../utils/fn.js';
|
import * as Fn from '../utils/fn.js';
|
||||||
import * as Guid from '../utils/guid.js';
|
import * as Guid from '../utils/guid.js';
|
||||||
@ -225,8 +228,8 @@ TextTrack.prototype.removeCue = function(removeCue) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Downloading stuff happens below this point
|
* Downloading stuff happens below this point
|
||||||
*/
|
*/
|
||||||
var parseCues = function(srcContent, track) {
|
var parseCues = function(srcContent, track) {
|
||||||
if (typeof window['WebVTT'] !== 'function') {
|
if (typeof window['WebVTT'] !== 'function') {
|
||||||
//try again a bit later
|
//try again a bit later
|
||||||
|
@ -1,10 +1,14 @@
|
|||||||
|
/**
|
||||||
|
* @file browser.js
|
||||||
|
*/
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
|
|
||||||
const USER_AGENT = window.navigator.userAgent;
|
const USER_AGENT = window.navigator.userAgent;
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Device is an iPhone
|
* Device is an iPhone
|
||||||
|
*
|
||||||
* @type {Boolean}
|
* @type {Boolean}
|
||||||
* @constant
|
* @constant
|
||||||
* @private
|
* @private
|
||||||
|
@ -1,11 +1,16 @@
|
|||||||
|
/**
|
||||||
|
* @file buffer.js
|
||||||
|
*/
|
||||||
import { createTimeRange } from './time-ranges.js';
|
import { createTimeRange } from './time-ranges.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Compute how much your video has been buffered
|
* Compute how much your video has been buffered
|
||||||
|
*
|
||||||
* @param {Object} Buffered object
|
* @param {Object} Buffered object
|
||||||
* @param {Number} Total duration
|
* @param {Number} Total duration
|
||||||
* @return {Number} Percent buffered of the total duration
|
* @return {Number} Percent buffered of the total duration
|
||||||
* @private
|
* @private
|
||||||
|
* @function bufferedPercent
|
||||||
*/
|
*/
|
||||||
export function bufferedPercent(buffered, duration) {
|
export function bufferedPercent(buffered, duration) {
|
||||||
var bufferedDuration = 0,
|
var bufferedDuration = 0,
|
||||||
|
@ -1,13 +1,18 @@
|
|||||||
|
/**
|
||||||
|
* @file dom.js
|
||||||
|
*/
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
import * as Guid from './guid.js';
|
import * as Guid from './guid.js';
|
||||||
import roundFloat from './round-float.js';
|
import roundFloat from './round-float.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Shorthand for document.getElementById()
|
* Shorthand for document.getElementById()
|
||||||
* Also allows for CSS (jQuery) ID syntax. But nothing other than IDs.
|
* Also allows for CSS (jQuery) ID syntax. But nothing other than IDs.
|
||||||
|
*
|
||||||
* @param {String} id Element ID
|
* @param {String} id Element ID
|
||||||
* @return {Element} Element with supplied ID
|
* @return {Element} Element with supplied ID
|
||||||
|
* @function getEl
|
||||||
*/
|
*/
|
||||||
export function getEl(id){
|
export function getEl(id){
|
||||||
if (id.indexOf('#') === 0) {
|
if (id.indexOf('#') === 0) {
|
||||||
@ -19,9 +24,11 @@ export function getEl(id){
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Creates an element and applies properties.
|
* Creates an element and applies properties.
|
||||||
|
*
|
||||||
* @param {String=} tagName Name of tag to be created.
|
* @param {String=} tagName Name of tag to be created.
|
||||||
* @param {Object=} properties Element properties to be applied.
|
* @param {Object=} properties Element properties to be applied.
|
||||||
* @return {Element}
|
* @return {Element}
|
||||||
|
* @function createEl
|
||||||
*/
|
*/
|
||||||
export function createEl(tagName='div', properties={}){
|
export function createEl(tagName='div', properties={}){
|
||||||
let el = document.createElement(tagName);
|
let el = document.createElement(tagName);
|
||||||
@ -32,10 +39,10 @@ export function createEl(tagName='div', properties={}){
|
|||||||
// Not remembering why we were checking for dash
|
// Not remembering why we were checking for dash
|
||||||
// but using setAttribute means you have to use getAttribute
|
// but using setAttribute means you have to use getAttribute
|
||||||
|
|
||||||
// The check for dash checks for the aria-* attributes, like aria-label, aria-valuemin.
|
// The check for dash checks for the aria- * attributes, like aria-label, aria-valuemin.
|
||||||
// The additional check for "role" is because the default method for adding attributes does not
|
// The additional check for "role" is because the default method for adding attributes does not
|
||||||
// add the attribute "role". My guess is because it's not a valid attribute in some namespaces, although
|
// add the attribute "role". My guess is because it's not a valid attribute in some namespaces, although
|
||||||
// browsers handle the attribute just fine. The W3C allows for aria-* attributes to be used in pre-HTML5 docs.
|
// browsers handle the attribute just fine. The W3C allows for aria- * attributes to be used in pre-HTML5 docs.
|
||||||
// http://www.w3.org/TR/wai-aria-primer/#ariahtml. Using setAttribute gets around this problem.
|
// http://www.w3.org/TR/wai-aria-primer/#ariahtml. Using setAttribute gets around this problem.
|
||||||
if (propName.indexOf('aria-') !== -1 || propName === 'role') {
|
if (propName.indexOf('aria-') !== -1 || propName === 'role') {
|
||||||
el.setAttribute(propName, val);
|
el.setAttribute(propName, val);
|
||||||
@ -49,9 +56,11 @@ export function createEl(tagName='div', properties={}){
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Insert an element as the first child node of another
|
* Insert an element as the first child node of another
|
||||||
|
*
|
||||||
* @param {Element} child Element to insert
|
* @param {Element} child Element to insert
|
||||||
* @param {[type]} parent Element to insert child into
|
* @param {Element} parent Element to insert child into
|
||||||
* @private
|
* @private
|
||||||
|
* @function insertElFirst
|
||||||
*/
|
*/
|
||||||
export function insertElFirst(child, parent){
|
export function insertElFirst(child, parent){
|
||||||
if (parent.firstChild) {
|
if (parent.firstChild) {
|
||||||
@ -65,13 +74,15 @@ export function insertElFirst(child, parent){
|
|||||||
* Element Data Store. Allows for binding data to an element without putting it directly on the element.
|
* Element Data Store. Allows for binding data to an element without putting it directly on the element.
|
||||||
* Ex. Event listeners are stored here.
|
* Ex. Event listeners are stored here.
|
||||||
* (also from jsninja.com, slightly modified and updated for closure compiler)
|
* (also from jsninja.com, slightly modified and updated for closure compiler)
|
||||||
|
*
|
||||||
* @type {Object}
|
* @type {Object}
|
||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
const elData = {};
|
const elData = {};
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Unique attribute name to store an element's guid in
|
* Unique attribute name to store an element's guid in
|
||||||
|
*
|
||||||
* @type {String}
|
* @type {String}
|
||||||
* @constant
|
* @constant
|
||||||
* @private
|
* @private
|
||||||
@ -80,8 +91,10 @@ const elIdAttr = 'vdata' + (new Date()).getTime();
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the cache object where data for an element is stored
|
* Returns the cache object where data for an element is stored
|
||||||
|
*
|
||||||
* @param {Element} el Element to store data for.
|
* @param {Element} el Element to store data for.
|
||||||
* @return {Object}
|
* @return {Object}
|
||||||
|
* @function getElData
|
||||||
*/
|
*/
|
||||||
export function getElData(el) {
|
export function getElData(el) {
|
||||||
let id = el[elIdAttr];
|
let id = el[elIdAttr];
|
||||||
@ -99,9 +112,11 @@ export function getElData(el) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns whether or not an element has cached data
|
* Returns whether or not an element has cached data
|
||||||
|
*
|
||||||
* @param {Element} el A dom element
|
* @param {Element} el A dom element
|
||||||
* @return {Boolean}
|
* @return {Boolean}
|
||||||
* @private
|
* @private
|
||||||
|
* @function hasElData
|
||||||
*/
|
*/
|
||||||
export function hasElData(el) {
|
export function hasElData(el) {
|
||||||
const id = el[elIdAttr];
|
const id = el[elIdAttr];
|
||||||
@ -115,8 +130,10 @@ export function hasElData(el) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Delete data for the element from the cache and the guid attr from getElementById
|
* Delete data for the element from the cache and the guid attr from getElementById
|
||||||
|
*
|
||||||
* @param {Element} el Remove data for an element
|
* @param {Element} el Remove data for an element
|
||||||
* @private
|
* @private
|
||||||
|
* @function removeElData
|
||||||
*/
|
*/
|
||||||
export function removeElData(el) {
|
export function removeElData(el) {
|
||||||
let id = el[elIdAttr];
|
let id = el[elIdAttr];
|
||||||
@ -143,8 +160,10 @@ export function removeElData(el) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Check if an element has a CSS class
|
* Check if an element has a CSS class
|
||||||
|
*
|
||||||
* @param {Element} element Element to check
|
* @param {Element} element Element to check
|
||||||
* @param {String} classToCheck Classname to check
|
* @param {String} classToCheck Classname to check
|
||||||
|
* @function hasElClass
|
||||||
*/
|
*/
|
||||||
export function hasElClass(element, classToCheck) {
|
export function hasElClass(element, classToCheck) {
|
||||||
return ((' ' + element.className + ' ').indexOf(' ' + classToCheck + ' ') !== -1);
|
return ((' ' + element.className + ' ').indexOf(' ' + classToCheck + ' ') !== -1);
|
||||||
@ -152,8 +171,10 @@ export function hasElClass(element, classToCheck) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Add a CSS class name to an element
|
* Add a CSS class name to an element
|
||||||
|
*
|
||||||
* @param {Element} element Element to add class name to
|
* @param {Element} element Element to add class name to
|
||||||
* @param {String} classToAdd Classname to add
|
* @param {String} classToAdd Classname to add
|
||||||
|
* @function addElClass
|
||||||
*/
|
*/
|
||||||
export function addElClass(element, classToAdd) {
|
export function addElClass(element, classToAdd) {
|
||||||
if (!hasElClass(element, classToAdd)) {
|
if (!hasElClass(element, classToAdd)) {
|
||||||
@ -163,8 +184,10 @@ export function addElClass(element, classToAdd) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Remove a CSS class name from an element
|
* Remove a CSS class name from an element
|
||||||
|
*
|
||||||
* @param {Element} element Element to remove from class name
|
* @param {Element} element Element to remove from class name
|
||||||
* @param {String} classToAdd Classname to remove
|
* @param {String} classToRemove Classname to remove
|
||||||
|
* @function removeElClass
|
||||||
*/
|
*/
|
||||||
export function removeElClass(element, classToRemove) {
|
export function removeElClass(element, classToRemove) {
|
||||||
if (!hasElClass(element, classToRemove)) {return;}
|
if (!hasElClass(element, classToRemove)) {return;}
|
||||||
@ -183,9 +206,11 @@ export function removeElClass(element, classToRemove) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Apply attributes to an HTML element.
|
* Apply attributes to an HTML element.
|
||||||
|
*
|
||||||
* @param {Element} el Target element.
|
* @param {Element} el Target element.
|
||||||
* @param {Object=} attributes Element attributes to be applied.
|
* @param {Object=} attributes Element attributes to be applied.
|
||||||
* @private
|
* @private
|
||||||
|
* @function setElAttributes
|
||||||
*/
|
*/
|
||||||
export function setElAttributes(el, attributes) {
|
export function setElAttributes(el, attributes) {
|
||||||
Object.getOwnPropertyNames(attributes).forEach(function(attrName){
|
Object.getOwnPropertyNames(attributes).forEach(function(attrName){
|
||||||
@ -204,9 +229,11 @@ export function setElAttributes(el, attributes) {
|
|||||||
* Attributes are not the same as properties. They're defined on the tag
|
* Attributes are not the same as properties. They're defined on the tag
|
||||||
* or with setAttribute (which shouldn't be used with HTML)
|
* or with setAttribute (which shouldn't be used with HTML)
|
||||||
* This will return true or false for boolean attributes.
|
* This will return true or false for boolean attributes.
|
||||||
|
*
|
||||||
* @param {Element} tag Element from which to get tag attributes
|
* @param {Element} tag Element from which to get tag attributes
|
||||||
* @return {Object}
|
* @return {Object}
|
||||||
* @private
|
* @private
|
||||||
|
* @function getElAttributes
|
||||||
*/
|
*/
|
||||||
export function getElAttributes(tag) {
|
export function getElAttributes(tag) {
|
||||||
var obj, knownBooleans, attrs, attrName, attrVal;
|
var obj, knownBooleans, attrs, attrName, attrVal;
|
||||||
@ -241,7 +268,12 @@ export function getElAttributes(tag) {
|
|||||||
return obj;
|
return obj;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Attempt to block the ability to select text while dragging controls
|
/**
|
||||||
|
* Attempt to block the ability to select text while dragging controls
|
||||||
|
*
|
||||||
|
* @return {Boolean}
|
||||||
|
* @method blockTextSelection
|
||||||
|
*/
|
||||||
export function blockTextSelection() {
|
export function blockTextSelection() {
|
||||||
document.body.focus();
|
document.body.focus();
|
||||||
document.onselectstart = function() {
|
document.onselectstart = function() {
|
||||||
@ -249,15 +281,27 @@ export function blockTextSelection() {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
// Turn off text selection blocking
|
/**
|
||||||
|
* Turn off text selection blocking
|
||||||
|
*
|
||||||
|
* @return {Boolean}
|
||||||
|
* @method unblockTextSelection
|
||||||
|
*/
|
||||||
export function unblockTextSelection() {
|
export function unblockTextSelection() {
|
||||||
document.onselectstart = function() {
|
document.onselectstart = function() {
|
||||||
return true;
|
return true;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
// Offset Left
|
/**
|
||||||
// getBoundingClientRect technique from John Resig http://ejohn.org/blog/getboundingclientrect-is-awesome/
|
* Offset Left
|
||||||
|
* getBoundingClientRect technique from
|
||||||
|
* John Resig http://ejohn.org/blog/getboundingclientrect-is-awesome/
|
||||||
|
*
|
||||||
|
* @param {Element} el Element from which to get offset
|
||||||
|
* @return {Object=}
|
||||||
|
* @method findElPosition
|
||||||
|
*/
|
||||||
export function findElPosition(el) {
|
export function findElPosition(el) {
|
||||||
let box;
|
let box;
|
||||||
|
|
||||||
|
@ -1,12 +1,14 @@
|
|||||||
/**
|
/**
|
||||||
* @fileoverview Event System (John Resig - Secrets of a JS Ninja http://jsninja.com/)
|
* @file events.js
|
||||||
|
*
|
||||||
|
* Event System (John Resig - Secrets of a JS Ninja http://jsninja.com/)
|
||||||
* (Original book version wasn't completely usable, so fixed some things and made Closure Compiler compatible)
|
* (Original book version wasn't completely usable, so fixed some things and made Closure Compiler compatible)
|
||||||
* This should work very similarly to jQuery's events, however it's based off the book version which isn't as
|
* This should work very similarly to jQuery's events, however it's based off the book version which isn't as
|
||||||
* robust as jquery's, so there's probably some differences.
|
* robust as jquery's, so there's probably some differences.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import * as Dom from './dom.js';
|
import * as Dom from './dom.js';
|
||||||
import * as Guid from './guid.js';
|
import * as Guid from './guid.js';
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
|
|
||||||
@ -15,9 +17,11 @@ import document from 'global/document';
|
|||||||
* It stores the handler function in a separate cache object
|
* It stores the handler function in a separate cache object
|
||||||
* and adds a generic handler to the element's event,
|
* and adds a generic handler to the element's event,
|
||||||
* along with a unique id (guid) to the element.
|
* along with a unique id (guid) to the element.
|
||||||
|
*
|
||||||
* @param {Element|Object} elem Element or object to bind listeners to
|
* @param {Element|Object} elem Element or object to bind listeners to
|
||||||
* @param {String|Array} type Type of event to bind to.
|
* @param {String|Array} type Type of event to bind to.
|
||||||
* @param {Function} fn Event listener.
|
* @param {Function} fn Event listener.
|
||||||
|
* @method on
|
||||||
*/
|
*/
|
||||||
export function on(elem, type, fn){
|
export function on(elem, type, fn){
|
||||||
if (Array.isArray(type)) {
|
if (Array.isArray(type)) {
|
||||||
@ -71,9 +75,11 @@ export function on(elem, type, fn){
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Removes event listeners from an element
|
* Removes event listeners from an element
|
||||||
|
*
|
||||||
* @param {Element|Object} elem Object to remove listeners from
|
* @param {Element|Object} elem Object to remove listeners from
|
||||||
* @param {String|Array=} type Type of listener to remove. Don't include to remove all events from element.
|
* @param {String|Array=} type Type of listener to remove. Don't include to remove all events from element.
|
||||||
* @param {Function} fn Specific listener to remove. Don't include to remove listeners for an event type.
|
* @param {Function} fn Specific listener to remove. Don't include to remove listeners for an event type.
|
||||||
|
* @method off
|
||||||
*/
|
*/
|
||||||
export function off(elem, type, fn) {
|
export function off(elem, type, fn) {
|
||||||
// Don't want to add a cache object through getElData if not needed
|
// Don't want to add a cache object through getElData if not needed
|
||||||
@ -125,9 +131,12 @@ export function off(elem, type, fn) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Trigger an event for an element
|
* Trigger an event for an element
|
||||||
|
*
|
||||||
* @param {Element|Object} elem Element to trigger an event on
|
* @param {Element|Object} elem Element to trigger an event on
|
||||||
* @param {Event|Object|String} event A string (the type) or an event object with a type attribute
|
* @param {Event|Object|String} event A string (the type) or an event object with a type attribute
|
||||||
* @param {Object} [hash] data hash to pass along with the event
|
* @param {Object} [hash] data hash to pass along with the event
|
||||||
|
* @return {Boolean=} Returned only if default was prevented
|
||||||
|
* @method trigger
|
||||||
*/
|
*/
|
||||||
export function trigger(elem, event, hash) {
|
export function trigger(elem, event, hash) {
|
||||||
// Fetches element data and a reference to the parent (for bubbling).
|
// Fetches element data and a reference to the parent (for bubbling).
|
||||||
@ -178,9 +187,11 @@ export function trigger(elem, event, hash) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Trigger a listener only once for an event
|
* Trigger a listener only once for an event
|
||||||
|
*
|
||||||
* @param {Element|Object} elem Element or object to
|
* @param {Element|Object} elem Element or object to
|
||||||
* @param {String|Array} type
|
* @param {String|Array} type Name/type of event
|
||||||
* @param {Function} fn
|
* @param {Function} fn Event handler function
|
||||||
|
* @method one
|
||||||
*/
|
*/
|
||||||
export function one(elem, type, fn) {
|
export function one(elem, type, fn) {
|
||||||
if (Array.isArray(type)) {
|
if (Array.isArray(type)) {
|
||||||
@ -197,9 +208,11 @@ export function one(elem, type, fn) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Fix a native event to have standard property values
|
* Fix a native event to have standard property values
|
||||||
|
*
|
||||||
* @param {Object} event Event object to fix
|
* @param {Object} event Event object to fix
|
||||||
* @return {Object}
|
* @return {Object}
|
||||||
* @private
|
* @private
|
||||||
|
* @method fixEvent
|
||||||
*/
|
*/
|
||||||
export function fixEvent(event) {
|
export function fixEvent(event) {
|
||||||
|
|
||||||
@ -307,9 +320,11 @@ export function fixEvent(event) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Clean up the listener cache and dispatchers
|
* Clean up the listener cache and dispatchers
|
||||||
|
*
|
||||||
* @param {Element|Object} elem Element to clean up
|
* @param {Element|Object} elem Element to clean up
|
||||||
* @param {String} type Type of event to clean up
|
* @param {String} type Type of event to clean up
|
||||||
* @private
|
* @private
|
||||||
|
* @method _cleanUpEvents
|
||||||
*/
|
*/
|
||||||
function _cleanUpEvents(elem, type) {
|
function _cleanUpEvents(elem, type) {
|
||||||
var data = Dom.getElData(elem);
|
var data = Dom.getElData(elem);
|
||||||
@ -343,11 +358,13 @@ function _cleanUpEvents(elem, type) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Loops through an array of event types and calls the requested method for each type.
|
* Loops through an array of event types and calls the requested method for each type.
|
||||||
|
*
|
||||||
* @param {Function} fn The event method we want to use.
|
* @param {Function} fn The event method we want to use.
|
||||||
* @param {Element|Object} elem Element or object to bind listeners to
|
* @param {Element|Object} elem Element or object to bind listeners to
|
||||||
* @param {String} type Type of event to bind to.
|
* @param {String} type Type of event to bind to.
|
||||||
* @param {Function} callback Event listener.
|
* @param {Function} callback Event listener.
|
||||||
* @private
|
* @private
|
||||||
|
* @function _handleMultipleEvents
|
||||||
*/
|
*/
|
||||||
function _handleMultipleEvents(fn, elem, types, callback) {
|
function _handleMultipleEvents(fn, elem, types, callback) {
|
||||||
types.forEach(function(type) {
|
types.forEach(function(type) {
|
||||||
|
@ -1,13 +1,18 @@
|
|||||||
|
/**
|
||||||
|
* @file fn.js
|
||||||
|
*/
|
||||||
import { newGUID } from './guid.js';
|
import { newGUID } from './guid.js';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Bind (a.k.a proxy or Context). A simple method for changing the context of a function
|
* Bind (a.k.a proxy or Context). A simple method for changing the context of a function
|
||||||
It also stores a unique id on the function so it can be easily removed from events
|
* It also stores a unique id on the function so it can be easily removed from events
|
||||||
|
*
|
||||||
* @param {*} context The object to bind as scope
|
* @param {*} context The object to bind as scope
|
||||||
* @param {Function} fn The function to be bound to a scope
|
* @param {Function} fn The function to be bound to a scope
|
||||||
* @param {Number=} uid An optional unique ID for the function to be set
|
* @param {Number=} uid An optional unique ID for the function to be set
|
||||||
* @return {Function}
|
* @return {Function}
|
||||||
* @private
|
* @private
|
||||||
|
* @method bind
|
||||||
*/
|
*/
|
||||||
export const bind = function(context, fn, uid) {
|
export const bind = function(context, fn, uid) {
|
||||||
// Make sure the function has a unique ID
|
// Make sure the function has a unique ID
|
||||||
|
@ -1,11 +1,15 @@
|
|||||||
/**
|
/**
|
||||||
|
* @file format-time.js
|
||||||
|
*
|
||||||
* Format seconds as a time string, H:MM:SS or M:SS
|
* Format seconds as a time string, H:MM:SS or M:SS
|
||||||
* Supplying a guide (in seconds) will force a number of leading zeros
|
* Supplying a guide (in seconds) will force a number of leading zeros
|
||||||
* to cover the length of the guide
|
* to cover the length of the guide
|
||||||
|
*
|
||||||
* @param {Number} seconds Number of seconds to be turned into a string
|
* @param {Number} seconds Number of seconds to be turned into a string
|
||||||
* @param {Number} guide Number (in seconds) to model the string after
|
* @param {Number} guide Number (in seconds) to model the string after
|
||||||
* @return {String} Time formatted as H:MM:SS or M:SS
|
* @return {String} Time formatted as H:MM:SS or M:SS
|
||||||
* @private
|
* @private
|
||||||
|
* @function formatTime
|
||||||
*/
|
*/
|
||||||
function formatTime(seconds, guide=seconds) {
|
function formatTime(seconds, guide=seconds) {
|
||||||
let s = Math.floor(seconds % 60);
|
let s = Math.floor(seconds % 60);
|
||||||
|
@ -1,4 +1,6 @@
|
|||||||
/**
|
/**
|
||||||
|
* @file guid.js
|
||||||
|
*
|
||||||
* Unique ID for an element or function
|
* Unique ID for an element or function
|
||||||
* @type {Number}
|
* @type {Number}
|
||||||
* @private
|
* @private
|
||||||
@ -7,6 +9,9 @@ let _guid = 1;
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the next unique ID
|
* Get the next unique ID
|
||||||
|
*
|
||||||
|
* @return {String}
|
||||||
|
* @function newGUID
|
||||||
*/
|
*/
|
||||||
export function newGUID() {
|
export function newGUID() {
|
||||||
return _guid++;
|
return _guid++;
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file log.js
|
||||||
|
*/
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -31,8 +34,9 @@ log.warn = function(){
|
|||||||
* Log messages to the console and history based on the type of message
|
* Log messages to the console and history based on the type of message
|
||||||
*
|
*
|
||||||
* @param {String} type The type of message, or `null` for `log`
|
* @param {String} type The type of message, or `null` for `log`
|
||||||
* @param {[type]} args The args to be passed to the log
|
* @param {Object} args The args to be passed to the log
|
||||||
* @private
|
* @private
|
||||||
|
* @method _logType
|
||||||
*/
|
*/
|
||||||
function _logType(type, args){
|
function _logType(type, args){
|
||||||
// convert args to an array to get array functions
|
// convert args to an array to get array functions
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file merge-options.js
|
||||||
|
*/
|
||||||
import merge from 'lodash-compat/object/merge';
|
import merge from 'lodash-compat/object/merge';
|
||||||
|
|
||||||
function isPlain(obj) {
|
function isPlain(obj) {
|
||||||
@ -8,13 +11,13 @@ function isPlain(obj) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Merge two options objects, recursively merging **only** plain object
|
* Merge two options objects, recursively merging **only* * plain object
|
||||||
* properties. Previously `deepMerge`.
|
* properties. Previously `deepMerge`.
|
||||||
*
|
*
|
||||||
* @param {Object} object The destination object
|
* @param {Object} object The destination object
|
||||||
* @param {...Object} source One or more objects to merge into the first
|
* @param {...Object} source One or more objects to merge into the first
|
||||||
*
|
|
||||||
* @returns {Object} The updated first object
|
* @returns {Object} The updated first object
|
||||||
|
* @function mergeOptions
|
||||||
*/
|
*/
|
||||||
export default function mergeOptions(object={}) {
|
export default function mergeOptions(object={}) {
|
||||||
|
|
||||||
|
@ -1,9 +1,13 @@
|
|||||||
/**
|
/**
|
||||||
|
* @file round-float.js
|
||||||
|
*
|
||||||
* Should round off a number to a decimal place
|
* Should round off a number to a decimal place
|
||||||
|
*
|
||||||
* @param {Number} num Number to round
|
* @param {Number} num Number to round
|
||||||
* @param {Number} dec Number of decimal places to round to
|
* @param {Number} dec Number of decimal places to round to
|
||||||
* @return {Number} Rounded number
|
* @return {Number} Rounded number
|
||||||
* @private
|
* @private
|
||||||
|
* @method roundFloat
|
||||||
*/
|
*/
|
||||||
const roundFloat = function(num, dec=0) {
|
const roundFloat = function(num, dec=0) {
|
||||||
return Math.round(num*Math.pow(10,dec))/Math.pow(10,dec);
|
return Math.round(num*Math.pow(10,dec))/Math.pow(10,dec);
|
||||||
|
@ -1,12 +1,16 @@
|
|||||||
/**
|
/**
|
||||||
|
* @file time-ranges.js
|
||||||
|
*
|
||||||
* Should create a fake TimeRange object
|
* Should create a fake TimeRange object
|
||||||
* Mimics an HTML5 time range instance, which has functions that
|
* Mimics an HTML5 time range instance, which has functions that
|
||||||
* return the start and end times for a range
|
* return the start and end times for a range
|
||||||
* TimeRanges are returned by the buffered() method
|
* TimeRanges are returned by the buffered() method
|
||||||
|
*
|
||||||
* @param {Number} start Start time in seconds
|
* @param {Number} start Start time in seconds
|
||||||
* @param {Number} end End time in seconds
|
* @param {Number} end End time in seconds
|
||||||
* @return {Object} Fake TimeRange object
|
* @return {Object} Fake TimeRange object
|
||||||
* @private
|
* @private
|
||||||
|
* @method createTimeRange
|
||||||
*/
|
*/
|
||||||
export function createTimeRange(start, end){
|
export function createTimeRange(start, end){
|
||||||
if (start === undefined && end === undefined) {
|
if (start === undefined && end === undefined) {
|
||||||
|
@ -1,8 +1,12 @@
|
|||||||
/**
|
/**
|
||||||
|
* @file to-title-case.js
|
||||||
|
*
|
||||||
* Uppercase the first letter of a string
|
* Uppercase the first letter of a string
|
||||||
|
*
|
||||||
* @param {String} string String to be uppercased
|
* @param {String} string String to be uppercased
|
||||||
* @return {String}
|
* @return {String}
|
||||||
* @private
|
* @private
|
||||||
|
* @method toTitleCase
|
||||||
*/
|
*/
|
||||||
function toTitleCase(string){
|
function toTitleCase(string){
|
||||||
return string.charAt(0).toUpperCase() + string.slice(1);
|
return string.charAt(0).toUpperCase() + string.slice(1);
|
||||||
|
@ -1,9 +1,14 @@
|
|||||||
|
/**
|
||||||
|
* @file url.js
|
||||||
|
*/
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Resolve and parse the elements of a URL
|
* Resolve and parse the elements of a URL
|
||||||
|
*
|
||||||
* @param {String} url The url to parse
|
* @param {String} url The url to parse
|
||||||
* @return {Object} An object of url details
|
* @return {Object} An object of url details
|
||||||
|
* @method parseUrl
|
||||||
*/
|
*/
|
||||||
export const parseUrl = function(url) {
|
export const parseUrl = function(url) {
|
||||||
const props = ['protocol', 'hostname', 'port', 'pathname', 'search', 'hash', 'host'];
|
const props = ['protocol', 'hostname', 'port', 'pathname', 'search', 'hash', 'host'];
|
||||||
@ -53,9 +58,11 @@ export const parseUrl = function(url) {
|
|||||||
/**
|
/**
|
||||||
* Get absolute version of relative URL. Used to tell flash correct URL.
|
* Get absolute version of relative URL. Used to tell flash correct URL.
|
||||||
* http://stackoverflow.com/questions/470832/getting-an-absolute-url-from-a-relative-one-ie6-issue
|
* http://stackoverflow.com/questions/470832/getting-an-absolute-url-from-a-relative-one-ie6-issue
|
||||||
|
*
|
||||||
* @param {String} url URL to make absolute
|
* @param {String} url URL to make absolute
|
||||||
* @return {String} Absolute URL
|
* @return {String} Absolute URL
|
||||||
* @private
|
* @private
|
||||||
|
* @method getAbsoluteURL
|
||||||
*/
|
*/
|
||||||
export const getAbsoluteURL = function(url){
|
export const getAbsoluteURL = function(url){
|
||||||
// Check if absolute URL
|
// Check if absolute URL
|
||||||
@ -74,6 +81,7 @@ export const getAbsoluteURL = function(url){
|
|||||||
*
|
*
|
||||||
* @param {String} path The fileName path like '/path/to/file.mp4'
|
* @param {String} path The fileName path like '/path/to/file.mp4'
|
||||||
* @returns {String} The extension in lower case or an empty string if no extension could be found.
|
* @returns {String} The extension in lower case or an empty string if no extension could be found.
|
||||||
|
* @method getFileExtension
|
||||||
*/
|
*/
|
||||||
export const getFileExtension = function(path) {
|
export const getFileExtension = function(path) {
|
||||||
if(typeof path === 'string'){
|
if(typeof path === 'string'){
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
/**
|
||||||
|
* @file video.js
|
||||||
|
*/
|
||||||
import document from 'global/document';
|
import document from 'global/document';
|
||||||
import * as setup from './setup';
|
import * as setup from './setup';
|
||||||
import Component from './component';
|
import Component from './component';
|
||||||
@ -27,16 +30,17 @@ if (typeof HTMLVideoElement === 'undefined') {
|
|||||||
/**
|
/**
|
||||||
* Doubles as the main function for users to create a player instance and also
|
* Doubles as the main function for users to create a player instance and also
|
||||||
* the main library object.
|
* the main library object.
|
||||||
*
|
|
||||||
* The `videojs` function can be used to initialize or retrieve a player.
|
* The `videojs` function can be used to initialize or retrieve a player.
|
||||||
*
|
* ```js
|
||||||
* var myPlayer = videojs('my_video_id');
|
* var myPlayer = videojs('my_video_id');
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {String|Element} id Video element or video element ID
|
* @param {String|Element} id Video element or video element ID
|
||||||
* @param {Object=} options Optional options object for config/settings
|
* @param {Object=} options Optional options object for config/settings
|
||||||
* @param {Function=} ready Optional ready callback
|
* @param {Function=} ready Optional ready callback
|
||||||
* @return {Player} A player instance
|
* @return {Player} A player instance
|
||||||
* @namespace
|
* @mixes videojs
|
||||||
|
* @method videojs
|
||||||
*/
|
*/
|
||||||
var videojs = function(id, options, ready){
|
var videojs = function(id, options, ready){
|
||||||
var tag; // Element of ID
|
var tag; // Element of ID
|
||||||
@ -88,8 +92,9 @@ var videojs = function(id, options, ready){
|
|||||||
// You have to wait at least once in case this script is loaded after your video in the DOM (weird behavior only with minified version)
|
// You have to wait at least once in case this script is loaded after your video in the DOM (weird behavior only with minified version)
|
||||||
setup.autoSetupTimeout(1, videojs);
|
setup.autoSetupTimeout(1, videojs);
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Current software version (semver)
|
* Current software version (semver)
|
||||||
|
*
|
||||||
* @type {String}
|
* @type {String}
|
||||||
*/
|
*/
|
||||||
videojs.VERSION = '__VERSION__';
|
videojs.VERSION = '__VERSION__';
|
||||||
@ -97,22 +102,26 @@ videojs.VERSION = '__VERSION__';
|
|||||||
/**
|
/**
|
||||||
* Get the global options object
|
* Get the global options object
|
||||||
*
|
*
|
||||||
* @returns {Object} The global options object
|
* @return {Object} The global options object
|
||||||
|
* @mixes videojs
|
||||||
|
* @method getGlobalOptions
|
||||||
*/
|
*/
|
||||||
videojs.getGlobalOptions = () => globalOptions;
|
videojs.getGlobalOptions = () => globalOptions;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set options that will apply to every player
|
* Set options that will apply to every player
|
||||||
*
|
* ```js
|
||||||
* videojs.setGlobalOptions({
|
* videojs.setGlobalOptions({
|
||||||
* autoplay: true
|
* autoplay: true
|
||||||
* });
|
* });
|
||||||
* // -> all players will autoplay by default
|
* // -> all players will autoplay by default
|
||||||
*
|
* ```
|
||||||
* NOTE: This will do a deep merge with the new options,
|
* NOTE: This will do a deep merge with the new options,
|
||||||
* not overwrite the entire global options object.
|
* not overwrite the entire global options object.
|
||||||
*
|
*
|
||||||
* @returns {Object} The updated global options object
|
* @return {Object} The updated global options object
|
||||||
|
* @mixes videojs
|
||||||
|
* @method setGlobalOptions
|
||||||
*/
|
*/
|
||||||
videojs.setGlobalOptions = function(newOptions) {
|
videojs.setGlobalOptions = function(newOptions) {
|
||||||
return mergeOptions(globalOptions, newOptions);
|
return mergeOptions(globalOptions, newOptions);
|
||||||
@ -121,7 +130,9 @@ videojs.setGlobalOptions = function(newOptions) {
|
|||||||
/**
|
/**
|
||||||
* Get an object with the currently created players, keyed by player ID
|
* Get an object with the currently created players, keyed by player ID
|
||||||
*
|
*
|
||||||
* @returns {Object} The created players
|
* @return {Object} The created players
|
||||||
|
* @mixes videojs
|
||||||
|
* @method getPlayers
|
||||||
*/
|
*/
|
||||||
videojs.getPlayers = function() {
|
videojs.getPlayers = function() {
|
||||||
return Player.players;
|
return Player.players;
|
||||||
@ -129,47 +140,49 @@ videojs.getPlayers = function() {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a component class object by name
|
* Get a component class object by name
|
||||||
*
|
* ```js
|
||||||
* var VjsButton = videojs.getComponent('Button');
|
* var VjsButton = videojs.getComponent('Button');
|
||||||
*
|
|
||||||
* // Create a new instance of the component
|
* // Create a new instance of the component
|
||||||
* var myButton = new VjsButton(myPlayer);
|
* var myButton = new VjsButton(myPlayer);
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
|
* @return {Component} Component identified by name
|
||||||
|
* @mixes videojs
|
||||||
|
* @method getComponent
|
||||||
*/
|
*/
|
||||||
videojs.getComponent = Component.getComponent;
|
videojs.getComponent = Component.getComponent;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Register a component so it can referred to by name
|
* Register a component so it can referred to by name
|
||||||
*
|
|
||||||
* Used when adding to other
|
* Used when adding to other
|
||||||
* components, either through addChild
|
* components, either through addChild
|
||||||
* `component.addChild('myComponent')`
|
* `component.addChild('myComponent')`
|
||||||
* or through default children options
|
* or through default children options
|
||||||
* `{ children: ['myComponent'] }`.
|
* `{ children: ['myComponent'] }`.
|
||||||
*
|
* ```js
|
||||||
* // Get a component to subclass
|
* // Get a component to subclass
|
||||||
* var VjsButton = videojs.getComponent('Button');
|
* var VjsButton = videojs.getComponent('Button');
|
||||||
*
|
|
||||||
* // Subclass the component (see 'extends' doc for more info)
|
* // Subclass the component (see 'extends' doc for more info)
|
||||||
* var MySpecialButton = videojs.extends(VjsButton, {});
|
* var MySpecialButton = videojs.extends(VjsButton, {});
|
||||||
*
|
|
||||||
* // Register the new component
|
* // Register the new component
|
||||||
* VjsButton.registerComponent('MySepcialButton', MySepcialButton);
|
* VjsButton.registerComponent('MySepcialButton', MySepcialButton);
|
||||||
*
|
|
||||||
* // (optionally) add the new component as a default player child
|
* // (optionally) add the new component as a default player child
|
||||||
* myPlayer.addChild('MySepcialButton');
|
* myPlayer.addChild('MySepcialButton');
|
||||||
*
|
* ```
|
||||||
* NOTE: You could also just initialize the component before adding.
|
* NOTE: You could also just initialize the component before adding.
|
||||||
* `component.addChild(new MyComponent());`
|
* `component.addChild(new MyComponent());`
|
||||||
*
|
*
|
||||||
* @param {String} The class name of the component
|
* @param {String} The class name of the component
|
||||||
* @param {Component} The component class
|
* @param {Component} The component class
|
||||||
* @returns {Component} The newly registered component
|
* @return {Component} The newly registered component
|
||||||
|
* @mixes videojs
|
||||||
|
* @method registerComponent
|
||||||
*/
|
*/
|
||||||
videojs.registerComponent = Component.registerComponent;
|
videojs.registerComponent = Component.registerComponent;
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* A suite of browser and device tests
|
* A suite of browser and device tests
|
||||||
|
*
|
||||||
* @type {Object}
|
* @type {Object}
|
||||||
*/
|
*/
|
||||||
videojs.browser = browser;
|
videojs.browser = browser;
|
||||||
@ -177,18 +190,16 @@ videojs.browser = browser;
|
|||||||
/**
|
/**
|
||||||
* Subclass an existing class
|
* Subclass an existing class
|
||||||
* Mimics ES6 subclassing with the `extends` keyword
|
* Mimics ES6 subclassing with the `extends` keyword
|
||||||
*
|
* ```js
|
||||||
* // Create a basic javascript 'class'
|
* // Create a basic javascript 'class'
|
||||||
* function MyClass(name){
|
* function MyClass(name){
|
||||||
* // Set a property at initialization
|
* // Set a property at initialization
|
||||||
* this.myName = name;
|
* this.myName = name;
|
||||||
* }
|
* }
|
||||||
*
|
|
||||||
* // Create an instance method
|
* // Create an instance method
|
||||||
* MyClass.prototype.sayMyName = function(){
|
* MyClass.prototype.sayMyName = function(){
|
||||||
* alert(this.myName);
|
* alert(this.myName);
|
||||||
* };
|
* };
|
||||||
*
|
|
||||||
* // Subclass the exisitng class and change the name
|
* // Subclass the exisitng class and change the name
|
||||||
* // when initializing
|
* // when initializing
|
||||||
* var MySubClass = videojs.extends(MyClass, {
|
* var MySubClass = videojs.extends(MyClass, {
|
||||||
@ -197,16 +208,17 @@ videojs.browser = browser;
|
|||||||
* MyClass.call(this, name)
|
* MyClass.call(this, name)
|
||||||
* }
|
* }
|
||||||
* });
|
* });
|
||||||
*
|
|
||||||
* // Create an instance of the new sub class
|
* // Create an instance of the new sub class
|
||||||
* var myInstance = new MySubClass('John');
|
* var myInstance = new MySubClass('John');
|
||||||
* myInstance.sayMyName(); // -> should alert "John"
|
* myInstance.sayMyName(); // -> should alert "John"
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {Function} The Class to subclass
|
* @param {Function} The Class to subclass
|
||||||
* @param {Object} An object including instace methods for the new class
|
* @param {Object} An object including instace methods for the new class
|
||||||
* Optionally including a `constructor` function
|
* Optionally including a `constructor` function
|
||||||
*
|
* @return {Function} The newly created subclass
|
||||||
* @returns {Function} The newly created subclass
|
* @mixes videojs
|
||||||
|
* @method extends
|
||||||
*/
|
*/
|
||||||
videojs.extends = extendsFn;
|
videojs.extends = extendsFn;
|
||||||
|
|
||||||
@ -215,7 +227,7 @@ videojs.extends = extendsFn;
|
|||||||
* Performs a deep merge like lodash.merge but **only merges plain objects**
|
* Performs a deep merge like lodash.merge but **only merges plain objects**
|
||||||
* (not arrays, elements, anything else)
|
* (not arrays, elements, anything else)
|
||||||
* Other values will be copied directly from the second object.
|
* Other values will be copied directly from the second object.
|
||||||
*
|
* ```js
|
||||||
* var defaultOptions = {
|
* var defaultOptions = {
|
||||||
* foo: true,
|
* foo: true,
|
||||||
* bar: {
|
* bar: {
|
||||||
@ -229,29 +241,29 @@ videojs.extends = extendsFn;
|
|||||||
* b: [4,5,6]
|
* b: [4,5,6]
|
||||||
* }
|
* }
|
||||||
* };
|
* };
|
||||||
*
|
|
||||||
* var result = videojs.mergeOptions(defaultOptions, newOptions);
|
* var result = videojs.mergeOptions(defaultOptions, newOptions);
|
||||||
* // result.foo = false;
|
* // result.foo = false;
|
||||||
* // result.bar.a = true;
|
* // result.bar.a = true;
|
||||||
* // result.bar.b = [4,5,6];
|
* // result.bar.b = [4,5,6];
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {Object} The options object whose values will be overriden
|
* @param {Object} The options object whose values will be overriden
|
||||||
* @param {Object} The options object with values to override the first
|
* @param {Object} The options object with values to override the first
|
||||||
* @param {Object} Any number of additional options objects
|
* @param {Object} Any number of additional options objects
|
||||||
*
|
*
|
||||||
* @returns {Object} a new object with the merged values
|
* @return {Object} a new object with the merged values
|
||||||
|
* @mixes videojs
|
||||||
|
* @method mergeOptions
|
||||||
*/
|
*/
|
||||||
videojs.mergeOptions = mergeOptions;
|
videojs.mergeOptions = mergeOptions;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create a Video.js player plugin
|
* Create a Video.js player plugin
|
||||||
*
|
|
||||||
* Plugins are only initialized when options for the plugin are included
|
* Plugins are only initialized when options for the plugin are included
|
||||||
* in the player options, or the plugin function on the player instance is
|
* in the player options, or the plugin function on the player instance is
|
||||||
* called.
|
* called.
|
||||||
*
|
|
||||||
* **See the plugin guide in the docs for a more detailed example**
|
* **See the plugin guide in the docs for a more detailed example**
|
||||||
*
|
* ```js
|
||||||
* // Make a plugin that alerts when the player plays
|
* // Make a plugin that alerts when the player plays
|
||||||
* videojs.plugin('myPlugin', function(myPluginOptions) {
|
* videojs.plugin('myPlugin', function(myPluginOptions) {
|
||||||
* myPluginOptions = myPluginOptions || {};
|
* myPluginOptions = myPluginOptions || {};
|
||||||
@ -263,9 +275,7 @@ videojs.mergeOptions = mergeOptions;
|
|||||||
* alert(alertText);
|
* alert(alertText);
|
||||||
* });
|
* });
|
||||||
* });
|
* });
|
||||||
*
|
|
||||||
* // USAGE EXAMPLES
|
* // USAGE EXAMPLES
|
||||||
*
|
|
||||||
* // EXAMPLE 1: New player with plugin options, call plugin immediately
|
* // EXAMPLE 1: New player with plugin options, call plugin immediately
|
||||||
* var player1 = videojs('idOne', {
|
* var player1 = videojs('idOne', {
|
||||||
* myPlugin: {
|
* myPlugin: {
|
||||||
@ -274,7 +284,6 @@ videojs.mergeOptions = mergeOptions;
|
|||||||
* });
|
* });
|
||||||
* // Click play
|
* // Click play
|
||||||
* // --> Should alert 'Custom text!'
|
* // --> Should alert 'Custom text!'
|
||||||
*
|
|
||||||
* // EXAMPLE 3: New player, initialize plugin later
|
* // EXAMPLE 3: New player, initialize plugin later
|
||||||
* var player3 = videojs('idThree');
|
* var player3 = videojs('idThree');
|
||||||
* // Click play
|
* // Click play
|
||||||
@ -286,21 +295,26 @@ videojs.mergeOptions = mergeOptions;
|
|||||||
* });
|
* });
|
||||||
* // Click play
|
* // Click play
|
||||||
* // --> Should alert 'Plugin added later!'
|
* // --> Should alert 'Plugin added later!'
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {String} The plugin name
|
* @param {String} The plugin name
|
||||||
* @param {Function} The plugin function that will be called with options
|
* @param {Function} The plugin function that will be called with options
|
||||||
|
* @mixes videojs
|
||||||
|
* @method plugin
|
||||||
*/
|
*/
|
||||||
videojs.plugin = plugin;
|
videojs.plugin = plugin;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adding languages so that they're available to all players.
|
* Adding languages so that they're available to all players.
|
||||||
*
|
* ```js
|
||||||
* videojs.addLanguage('es', { 'Hello': 'Hola' });
|
* videojs.addLanguage('es', { 'Hello': 'Hola' });
|
||||||
|
* ```
|
||||||
*
|
*
|
||||||
* @param {String} code The language code or dictionary property
|
* @param {String} code The language code or dictionary property
|
||||||
* @param {Object} data The data values to be translated
|
* @param {Object} data The data values to be translated
|
||||||
*
|
|
||||||
* @return {Object} The resulting language dictionary object
|
* @return {Object} The resulting language dictionary object
|
||||||
|
* @mixes videojs
|
||||||
|
* @method addLanguage
|
||||||
*/
|
*/
|
||||||
videojs.addLanguage = function(code, data){
|
videojs.addLanguage = function(code, data){
|
||||||
code = ('' + code).toLowerCase();
|
code = ('' + code).toLowerCase();
|
||||||
@ -324,7 +338,7 @@ videojs.addLanguage = function(code, data){
|
|||||||
// assign(module.exports[name], component);
|
// assign(module.exports[name], component);
|
||||||
// });
|
// });
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Custom Universal Module Definition (UMD)
|
* Custom Universal Module Definition (UMD)
|
||||||
*
|
*
|
||||||
* Video.js will never be a non-browser lib so we can simplify UMD a bunch and
|
* Video.js will never be a non-browser lib so we can simplify UMD a bunch and
|
||||||
|
@ -1,13 +1,14 @@
|
|||||||
import * as Url from './utils/url.js';
|
/**
|
||||||
|
* @file xhr.js
|
||||||
|
*/
|
||||||
|
import * as Url from './utils/url.js';
|
||||||
import log from './utils/log.js';
|
import log from './utils/log.js';
|
||||||
import mergeOptions from './utils/merge-options.js';
|
import mergeOptions from './utils/merge-options.js';
|
||||||
import window from 'global/window';
|
import window from 'global/window';
|
||||||
|
|
||||||
/**
|
/*
|
||||||
* Simple http request for retrieving external files (e.g. text tracks)
|
* Simple http request for retrieving external files (e.g. text tracks)
|
||||||
*
|
|
||||||
* ##### Example
|
* ##### Example
|
||||||
*
|
|
||||||
* // using url string
|
* // using url string
|
||||||
* videojs.xhr('http://example.com/myfile.vtt', function(error, response, responseBody){});
|
* videojs.xhr('http://example.com/myfile.vtt', function(error, response, responseBody){});
|
||||||
*
|
*
|
||||||
@ -23,15 +24,15 @@ import window from 'global/window';
|
|||||||
* // successful, do something with the response
|
* // successful, do something with the response
|
||||||
* }
|
* }
|
||||||
* });
|
* });
|
||||||
*
|
* /////////////
|
||||||
*
|
|
||||||
* API is modeled after the Raynos/xhr, which we hope to use after
|
* API is modeled after the Raynos/xhr, which we hope to use after
|
||||||
* getting browserify implemented.
|
* getting browserify implemented.
|
||||||
* https://github.com/Raynos/xhr/blob/master/index.js
|
* https://github.com/Raynos/xhr/blob/master/index.js
|
||||||
*
|
*
|
||||||
* @param {Object|String} options Options block or URL string
|
* @param {Object|String} options Options block or URL string
|
||||||
* @param {Function} callback The callback function
|
* @param {Function} callback The callback function
|
||||||
* @returns {Object} The request
|
* @return {Object} The request
|
||||||
|
* @method xhr
|
||||||
*/
|
*/
|
||||||
var xhr = function(options, callback){
|
var xhr = function(options, callback){
|
||||||
let abortTimeout;
|
let abortTimeout;
|
||||||
@ -46,7 +47,7 @@ var xhr = function(options, callback){
|
|||||||
// Merge with default options
|
// Merge with default options
|
||||||
mergeOptions({
|
mergeOptions({
|
||||||
method: 'GET',
|
method: 'GET',
|
||||||
timeout: 45 * 1000
|
timeout: 45 * 1000
|
||||||
}, options);
|
}, options);
|
||||||
|
|
||||||
callback = callback || function(){};
|
callback = callback || function(){};
|
||||||
|
Loading…
x
Reference in New Issue
Block a user