1 /** The minplayer namespace. */
  2 var minplayer = minplayer || {};
  3 
  4 /** All the media player implementations */
  5 minplayer.players = minplayer.players || {};
  6 
  7 /**
  8  * @constructor
  9  * @extends minplayer.players.base
 10  * @class The Limelight media player.
 11  *
 12  * @param {object} context The jQuery context.
 13  * @param {object} options This components options.
 14  */
 15 minplayer.players.limelight = function(context, options) {
 16 
 17   // Derive from players base.
 18   minplayer.players.flash.call(this, context, options);
 19 };
 20 
 21 /** Derive from minplayer.players.flash. */
 22 minplayer.players.limelight.prototype = new minplayer.players.flash();
 23 
 24 /** Reset the constructor. */
 25 minplayer.players.limelight.prototype.constructor = minplayer.players.limelight;
 26 
 27 /**
 28  * @see minplayer.plugin.construct
 29  * @this minplayer.players.limelight
 30  */
 31 minplayer.players.limelight.prototype.construct = function() {
 32 
 33   // Call the players.flash constructor.
 34   minplayer.players.flash.prototype.construct.call(this);
 35 
 36   // Set the plugin name within the options.
 37   this.options.pluginName = 'limelight';
 38 };
 39 
 40 /**
 41  * @see minplayer.players.base#getPriority
 42  * @return {number} The priority of this media player.
 43  */
 44 minplayer.players.limelight.getPriority = function() {
 45   return 10;
 46 };
 47 
 48 /**
 49  * @see minplayer.players.base#canPlay
 50  *
 51  * @param {object} file A {@link minplayer.file} object.
 52  * @return {boolean} If this player can play this media type.
 53  */
 54 minplayer.players.limelight.canPlay = function(file) {
 55 
 56   // Check for the mimetype for limelight.
 57   if (file.mimetype === 'video/limelight') {
 58     return true;
 59   }
 60 
 61   // If the path is a limelight path, then return true.
 62   var regex = /.*limelight\.com.*/i;
 63   return (file.path.search(regex) === 0);
 64 };
 65 
 66 /**
 67  * Return the ID for a provided media file.
 68  *
 69  * @param {object} file A {@link minplayer.file} object.
 70  * @return {string} The ID for the provided media.
 71  */
 72 minplayer.players.limelight.getMediaId = function(file) {
 73   var regex = /.*limelight\.com.*mediaId=([a-zA-Z0-9]+)/i;
 74   if (file.path.search(regex) === 0) {
 75     return file.path.match(regex)[1];
 76   }
 77   else {
 78     return file.path;
 79   }
 80 };
 81 
 82 /**
 83  * Register this limelight player so that multiple players can be present
 84  * on the same page without event collision.
 85  */
 86 minplayer.players.limelight.prototype.register = function() {
 87 
 88   // Register the limelight player.
 89   window.delvePlayerCallback = function(playerId, event, data) {
 90 
 91     // Get the main player ID.
 92     var id = playerId.replace('-player', '');
 93 
 94     // Dispatch this event to the correct player.
 95     jQuery.each(minplayer.get(id, 'media'), function(key, media) {
 96       media.onMediaUpdate(event, data);
 97     });
 98   };
 99 };
100 
101 /**
102  * The media update method.
103  *
104  * @param {string} event The event that was triggered.
105  * @param {object} data The event object.
106  */
107 minplayer.players.limelight.prototype.onMediaUpdate = function(event, data) {
108 
109   // Switch on the event name.
110   switch (event) {
111     case 'onPlayerLoad':
112       this.onReady();
113       break;
114 
115     case 'onMediaLoad':
116       // If this media has already completed, then pause it and return...
117       if (this.complete) {
118         this.pause();
119         this.onPaused();
120         return;
121       }
122 
123       this.shouldSeek = (this.startTime > 0);
124       this.onLoaded();
125       break;
126 
127     case 'onMediaComplete':
128       this.complete = true;
129       this.onComplete();
130       break;
131 
132     case 'onPlayheadUpdate':
133 
134       // Make sure we say this is playing.
135       if (data.positionInMilliseconds && !this.playing && !this.complete) {
136         this.onPlaying();
137       }
138 
139       // Set the complete flag to false.
140       this.complete = false;
141 
142       // Set the duration and current time.
143       if (this.shouldSeek && this.seekValue) {
144         this.shouldSeek = false;
145         this.seek(this.seekValue);
146       }
147       else {
148         this.duration.set(data.durationInMilliseconds / 1000);
149         this.currentTime.set(data.positionInMilliseconds / 1000);
150       }
151       break;
152 
153     case 'onError':
154       this.onError();
155       break;
156 
157     case 'onPlayStateChanged':
158       if (data.isPlaying) {
159         this.onPlaying();
160       }
161       else if (data.isBusy) {
162         this.onWaiting();
163       }
164       else {
165         this.onPaused();
166       }
167       break;
168   }
169 };
170 
171 /**
172  * @see minplayer.players.base#create
173  * @return {object} The media player entity.
174  */
175 minplayer.players.limelight.prototype.createPlayer = function() {
176   minplayer.players.flash.prototype.createPlayer.call(this);
177 
178   // Insert the embed.js.
179   var tag = document.createElement('script');
180   tag.src = 'https://assets.delvenetworks.com/player/embed.js';
181   var firstScriptTag = document.getElementsByTagName('script')[0];
182   firstScriptTag.parentNode.insertBefore(tag, firstScriptTag);
183 
184   // Now register this player.
185   this.register();
186 
187   // Get the FlashVars.
188   var flashVars = {
189     'deepLink': 'true',
190     'autoplay': this.options.autoplay ? 'true' : 'false',
191     'startQuality': 'HD'
192   }, regex = null;
193 
194   // Get the channel for this player.
195   var channel = this.options.channel;
196   if (!channel) {
197     regex = /.*limelight\.com.*channelId=([a-zA-Z0-9]+)/i;
198     if (this.mediaFile.path.search(regex) === 0) {
199       channel = this.mediaFile.path.match(regex)[1];
200     }
201   }
202 
203   // Set the channel.
204   if (channel && this.mediaFile.queueType === 'media') {
205     flashVars.adConfigurationChannelId = channel;
206   }
207 
208   // Get the playerForm for this player.
209   var playerForm = this.options.playerForm;
210   if (!playerForm) {
211     regex = /.*limelight\.com.*playerForm=([a-zA-Z0-9]+)/i;
212     if (this.mediaFile.path.search(regex) === 0) {
213       playerForm = this.mediaFile.path.match(regex)[1];
214     }
215   }
216 
217   // Set the player form.
218   if (playerForm) {
219     flashVars.playerForm = playerForm;
220   }
221 
222   // Add the media Id to the flashvars.
223   flashVars.mediaId = this.mediaFile.id;
224 
225   // Set the player ID.
226   var playerId = this.options.id + '-player';
227 
228   // Check the embed code every second.
229   setTimeout(function checkLimelight() {
230     if (window.hasOwnProperty('LimelightPlayerUtil')) {
231       window.LimelightPlayerUtil.initEmbed(playerId);
232     }
233     else {
234       setTimeout(checkLimelight, 1000);
235     }
236   }, 1000);
237 
238   // Return a flash media player object.
239   return this.getFlash({
240     swf: document.location.protocol + '//assets.delvenetworks.com/player/loader.swf',
241     id: playerId,
242     width: this.options.width,
243     height: '100%',
244     flashvars: flashVars,
245     wmode: this.options.wmode
246   });
247 };
248 
249 /**
250  * @see minplayer.players.base#play
251  */
252 minplayer.players.limelight.prototype.play = function(callback) {
253   minplayer.players.flash.prototype.play.call(this, function() {
254     this.player.doPlay();
255     if (callback) {
256       callback.call(this);
257     }
258   });
259 };
260 
261 /**
262  * @see minplayer.players.base#pause
263  */
264 minplayer.players.limelight.prototype.pause = function(callback) {
265   minplayer.players.flash.prototype.pause.call(this, function() {
266     this.player.doPause();
267     if (callback) {
268       callback.call(this);
269     }
270   });
271 };
272 
273 /**
274  * @see minplayer.players.base#stop
275  */
276 minplayer.players.limelight.prototype.stop = function(callback) {
277   minplayer.players.flash.prototype.stop.call(this, function() {
278     this.player.doPause();
279     if (callback) {
280       callback.call(this);
281     }
282   });
283 };
284 
285 /**
286  * @see minplayer.players.base#_seek
287  */
288 minplayer.players.limelight.prototype._seek = function(pos) {
289   this.seekValue = pos;
290   this.player.doSeekToSecond(pos);
291 };
292 
293 /**
294  * @see minplayer.players.base#setVolume
295  */
296 minplayer.players.limelight.prototype.setVolume = function(vol, callback) {
297   minplayer.players.flash.prototype.setVolume.call(this, vol, function() {
298     this.player.doSetVolume(vol);
299     if (callback) {
300       callback.call(this);
301     }
302   });
303 };
304 
305 /**
306  * @see minplayer.players.base#getVolume
307  */
308 minplayer.players.limelight.prototype._getVolume = function(callback) {
309   callback(this.player.doGetVolume());
310 };
311 
312 /**
313  * Perform the Limelight Search Inside.
314  *
315  * @param {string} query The query to search for.
316  */
317 minplayer.players.limelight.prototype.search = function(query) {
318   this.whenReady(function() {
319     this.player.doSearch(query);
320   });
321 };
322