Merge branch 'MDL-69521' of https://github.com/stronk7/moodle into master
[moodle.git] / media / player / videojs / amd / src / loader.js
1 // This file is part of Moodle - http://moodle.org/
2 //
3 // Moodle is free software: you can redistribute it and/or modify
4 // it under the terms of the GNU General Public License as published by
5 // the Free Software Foundation, either version 3 of the License, or
6 // (at your option) any later version.
7 //
8 // Moodle is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11 // GNU General Public License for more details.
12 //
13 // You should have received a copy of the GNU General Public License
14 // along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
16 /**
17  * Video JS loader.
18  *
19  * This takes care of applying the filter on content which was dynamically loaded.
20  *
21  * @module     media_videojs/loader
22  * @package    media_videojs
23  * @copyright  2016 Frédéric Massart - FMCorz.net
24  * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
25  */
27 import Config from 'core/config';
28 import Event from 'core/event';
29 import jQuery from 'jquery';
30 import Ajax from 'core/ajax';
31 import LocalStorage from 'core/localstorage';
32 import Notification from 'core/notification';
34 /**
35  * Whether this is the first load of videojs module.
36  */
37 let firstLoad;
39 /**
40  * The language that is used in the player
41  */
42 let language;
44 /**
45  * Set-up.
46  *
47  * Adds the listener for the event to then notify video.js.
48  * @param {string} lang Language to be used in the player
49  */
50 export const setUp = (lang) => {
51     language = lang;
52     firstLoad = true;
53     // Notify Video.js about the nodes already present on the page.
54     notifyVideoJS(null, jQuery('body'));
55     // We need to call popover automatically if nodes are added to the page later.
56     Event.getLegacyEvents().done((events) => {
57         jQuery(document).on(events.FILTER_CONTENT_UPDATED, notifyVideoJS);
58     });
59 };
61 /**
62  * Notify video.js of new nodes.
63  *
64  * @param {Event} e The event.
65  * @param {NodeList} nodes List of new nodes.
66  */
67 const notifyVideoJS = (e, nodes) => {
68     const selector = '.mediaplugin_videojs';
69     const langStrings = getLanguageJson();
71     // Find the descendants matching the expected parent of the audio and video
72     // tags. Then also addBack the nodes matching the same selector. Finally,
73     // we find the audio and video tags contained in those parents. Kind thanks
74     // to jQuery for the simplicity.
75     nodes.find(selector)
76         .addBack(selector)
77         .find('audio, video').each((index, element) => {
78             const id = jQuery(element).attr('id');
79             const config = jQuery(element).data('setup-lazy');
80             const modulePromises = [import('media_videojs/video-lazy')];
82             if (config.techOrder && config.techOrder.indexOf('youtube') !== -1) {
83                 // Add YouTube to the list of modules we require.
84                 modulePromises.push(import('media_videojs/Youtube-lazy'));
85             }
86             if (config.techOrder && config.techOrder.indexOf('flash') !== -1) {
87                 // Add Flash to the list of modules we require.
88                 modulePromises.push(import('media_videojs/videojs-flash-lazy'));
89             }
90             Promise.all([langStrings, ...modulePromises])
91             .then(([langJson, videojs]) => {
92                 if (firstLoad) {
93                     videojs.options.flash.swf = `${Config.wwwroot}/media/player/videojs/videojs/video-js.swf`;
94                     videojs.addLanguage(language, langJson);
96                     firstLoad = false;
97                 }
98                 videojs(id, config);
99                 return;
100             })
101             .catch(Notification.exception);
102         });
103 };
105 /**
106  * Returns the json object of the language strings to be used in the player.
107  *
108  * @returns {Promise}
109  */
110 const getLanguageJson = () => {
111     const cached = JSON.parse(LocalStorage.get('media_videojs') || '{}');
112     if (language in cached) {
113         return Promise.resolve(cached[language]);
114     }
116     const request = {
117         methodname: 'media_videojs_get_language',
118         args: {
119             lang: language
120         },
121     };
122     return Ajax.call([request])[0].then(result => {
123         cached[language] = JSON.parse(result);
124         LocalStorage.set('media_videojs', JSON.stringify(cached));
126         return cached[language];
127     });
128 };