1/* 2 * jQuery Media Plugin for converting elements into rich media content. 3 * 4 * Examples and documentation at: http://malsup.com/jquery/media/ 5 * Copyright (c) 2007-2010 M. Alsup 6 * Dual licensed under the MIT and GPL licenses: 7 * http://www.opensource.org/licenses/mit-license.php 8 * http://www.gnu.org/licenses/gpl.html 9 * 10 * @author: M. Alsup 11 * @version: 0.99 (05-JUN-2013) 12 * @requires jQuery v1.1.2 or later 13 * $Id: jquery.media.js 2460 2007-07-23 02:53:15Z malsup $ 14 * 15 * Supported Media Players: 16 * - Flash 17 * - Quicktime 18 * - Real Player 19 * - Silverlight 20 * - Windows Media Player 21 * - iframe 22 * 23 * Supported Media Formats: 24 * Any types supported by the above players, such as: 25 * Video: asf, avi, flv, mov, mpg, mpeg, mp4, qt, smil, swf, wmv, 3g2, 3gp 26 * Audio: aif, aac, au, gsm, mid, midi, mov, mp3, m4a, snd, rm, wav, wma 27 * Other: bmp, html, pdf, psd, qif, qtif, qti, tif, tiff, xaml 28 * 29 * Thanks to Mark Hicken and Brent Pedersen for helping me debug this on the Mac! 30 * Thanks to Dan Rossi for numerous bug reports and code bits! 31 * Thanks to Skye Giordano for several great suggestions! 32 * Thanks to Richard Connamacher for excellent improvements to the non-IE behavior! 33 */ 34/*global SWFObject alert Sys */ 35/*jshint forin:false */ 36;(function($) { 37"use strict"; 38 39var mode = document.documentMode || 0; 40var msie = /MSIE/.test(navigator.userAgent); 41var lameIE = msie && (/MSIE (6|7|8)\.0/.test(navigator.userAgent) || mode < 9); 42 43/** 44 * Chainable method for converting elements into rich media. 45 * 46 * @param options 47 * @param callback fn invoked for each matched element before conversion 48 * @param callback fn invoked for each matched element after conversion 49 */ 50$.fn.media = function(options, f1, f2) { 51 if (options == 'undo') { 52 return this.each(function() { 53 var $this = $(this); 54 var html = $this.data('media.origHTML'); 55 if (html) 56 $this.replaceWith(html); 57 }); 58 } 59 60 return this.each(function() { 61 if (typeof options == 'function') { 62 f2 = f1; 63 f1 = options; 64 options = {}; 65 } 66 var o = getSettings(this, options); 67 68 var r = getTypesRegExp(); 69 var m = r.exec(o.src.toLowerCase()) || ['']; 70 var fn; 71 72 // pre-conversion callback, passes original element and fully populated options 73 // only if it is a media link!!! 74 if (typeof f1 == 'function' && m != '') f1(this, o); 75 76 if (o.type) 77 m[0] = o.type; 78 else 79 m.shift(); 80 81 for (var i=0; i < m.length; i++) { 82 fn = m[i].toLowerCase(); 83 if (isDigit(fn[0])) fn = 'fn' + fn; // fns can't begin with numbers 84 if (!$.fn.media[fn]) 85 continue; // unrecognized media type 86 // normalize autoplay settings 87 var player = $.fn.media[fn+'_player']; 88 if (!o.params) o.params = {}; 89 if (player) { 90 var num = player.autoplayAttr == 'autostart'; 91 o.params[player.autoplayAttr || 'autoplay'] = num ? (o.autoplay ? 1 : 0) : o.autoplay ? true : false; 92 } 93 var $div = $.fn.media[fn](this, o); 94 95 $div.css('backgroundColor', o.bgColor).width(o.width); 96 97 if (o.canUndo) { 98 var $temp = $('<div></div>').append(this); 99 $div.data('media.origHTML', $temp.html()); // store original markup 100 } 101 102 // post-conversion callback, passes original element, new div element and fully populated options 103 if (typeof f2 == 'function') f2(this, $div[0], o, player.name); 104 break; 105 } 106 }); 107}; 108 109/** 110 * Non-chainable method for adding or changing file format / player mapping 111 * @name mapFormat 112 * @param String format File format extension (ie: mov, wav, mp3) 113 * @param String player Player name to use for the format (one of: flash, quicktime, realplayer, winmedia, silverlight or iframe 114 */ 115$.fn.media.mapFormat = function(format, player) { 116 if (!format || !player || !$.fn.media.defaults.players[player]) return; // invalid 117 format = format.toLowerCase(); 118 if (isDigit(format[0])) format = 'fn' + format; 119 $.fn.media[format] = $.fn.media[player]; 120 $.fn.media[format+'_player'] = $.fn.media.defaults.players[player]; 121}; 122 123// global defautls; override as needed 124$.fn.media.defaults = { 125 standards: true, // use object tags only (no embeds for non-IE browsers) 126 canUndo: true, // tells plugin to store the original markup so it can be reverted via: $(sel).mediaUndo() 127 width: 400, 128 height: 400, 129 autoplay: 0, // normalized cross-player setting 130 bgColor: '#ffffff', // background color 131 params: { wmode: 'transparent'}, // added to object element as param elements; added to embed element as attrs 132 attrs: {}, // added to object and embed elements as attrs 133 flvKeyName: 'file', // key used for object src param (thanks to Andrea Ercolino) 134 flashvars: {}, // added to flash content as flashvars param/attr 135 flashVersion: '7', // required flash version 136 expressInstaller: null, // src for express installer 137 138 // default flash video and mp3 player (@see: http://jeroenwijering.com/?item=Flash_Media_Player) 139 flvPlayer: 'mediaplayer.swf', 140 mp3Player: 'mediaplayer.swf', 141
142 // @see http://msdn2.microsoft.com/en-us/library/bb412401.aspx 143 silverlight: { 144 inplaceInstallPrompt: 'true', // display in-place install prompt? 145 isWindowless: 'true', // windowless mode (false for wrapping markup) 146 framerate: '24', // maximum framerate 147 version: '0.9', // Silverlight version 148 onError: null, // onError callback 149 onLoad: null, // onLoad callback 150 initParams: null, // object init params 151 userContext: null // callback arg passed to the load callback 152 } 153}; 154 155// Media Players; think twice before overriding 156$.fn.media.defaults.players = { 157 flash: { 158 name: 'flash', 159 title: 'Flash', 160 types: 'flv,mp3,swf', 161 mimetype: 'application/x-shockwave-flash', 162 pluginspage: 'http://www.adobe.com/go/getflashplayer', 163 ieAttrs: { 164 classid: 'clsid:d27cdb6e-ae6d-11cf-96b8-444553540000', 165 type: 'application/x-oleobject', 166 codebase: 'http://fpdownload.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=' + $.fn.media.defaults.flashVersion 167 } 168 }, 169 quicktime: { 170 name: 'quicktime', 171 title: 'QuickTime', 172 mimetype: 'video/quicktime', 173 pluginspage: 'http://www.apple.com/quicktime/download/', 174 types: 'aif,aiff,aac,au,bmp,gsm,mov,mid,midi,mpg,mpeg,mp4,m4a,psd,qt,qtif,qif,qti,snd,tif,tiff,wav,3g2,3gp', 175 ieAttrs: { 176 classid: 'clsid:02BF25D5-8C17-4B23-BC80-D3488ABDDC6B', 177 codebase: 'http://www.apple.com/qtactivex/qtplugin.cab' 178 } 179 }, 180 realplayer: { 181 name: 'real', 182 title: 'RealPlayer', 183 types: 'ra,ram,rm,rpm,rv,smi,smil', 184 mimetype: 'audio/x-pn-realaudio-plugin', 185 pluginspage: 'http://www.real.com/player/', 186 autoplayAttr: 'autostart', 187 ieAttrs: { 188 classid: 'clsid:CFCDAA03-8BE4-11cf-B84B-0020AFBBCCFA' 189 } 190 }, 191 winmedia: { 192 name: 'winmedia', 193 title: 'Windows Media', 194 types: 'asx,asf,avi,wma,wmv', 195 mimetype: isFirefoxWMPPluginInstalled() ? 'application/x-ms-wmp' : 'application/x-mplayer2', 196 pluginspage: 'http://www.microsoft.com/Windows/MediaPlayer/', 197 autoplayAttr: 'autostart', 198 oUrl: 'url', 199 ieAttrs: { 200 classid: 'clsid:6BF52A52-394A-11d3-B153-00C04F79FAA6', 201 type: 'application/x-oleobject' 202 } 203 }, 204 // special cases 205 img: { 206 name: 'img', 207 title: 'Image', 208 types: 'gif,png,jpg' 209 },/* 210 iframe: { 211 name: 'iframe', 212 types: 'html,pdf' 213 },*/ 214 silverlight: { 215 name: 'silverlight', 216 types: 'xaml' 217 } 218}; 219 220// 221// everything below here is private 222// 223 224 225// detection script for FF WMP plugin (http://www.therossman.org/experiments/wmp_play.html) 226// (hat tip to Mark Ross for this script) 227function isFirefoxWMPPluginInstalled() { 228 var plugs = navigator.plugins || []; 229 for (var i = 0; i < plugs.length; i++) { 230 var plugin = plugs[i]; 231 if (plugin['filename'] == 'np-mswmp.dll') 232 return true; 233 } 234 return false; 235} 236 237var counter = 1; 238 239for (var player in $.fn.media.defaults.players) { 240 var types = $.fn.media.defaults.players[player].types; 241 $.each(types.split(','), function(i,o) { 242 if (isDigit(o[0])) o = 'fn' + o; 243 $.fn.media[o] = $.fn.media[player] = getGenerator(player); 244 $.fn.media[o+'_player'] = $.fn.media.defaults.players[player]; 245 }); 246} 247 248function getTypesRegExp() { 249 var types = ''; 250 for (var player in $.fn.media.defaults.players) { 251 if (types.length) types += ','; 252 types += $.fn.media.defaults.players[player].types; 253 } 254 return new RegExp('\\.(' + types.replace(/,/ig,'|') + ')\\b'); 255} 256 257function getGenerator(player) { 258 return function(el, options) { 259 return generate(el, options, player); 260 }; 261} 262 263function isDigit(c) { 264 return '0123456789'.indexOf(c) > -1; 265} 266 267// flatten all possible options: global defaults, meta, option obj 268function getSettings(el, options) { 269 options = options || {}; 270 var a, n; 271 var $el = $(el); 272 var cls = el.className || ''; 273 // support metadata plugin (v1.0 and v2.0) 274 var meta = $.metadata ? $el.metadata() : $.meta ? $el.data() : {}; 275 meta = meta || {}; 276 var w = meta.width || parseInt(((cls.match(/\bw:(\d+)/)||[])[1]||0),10) || parseInt(((cls.match(/\bwidth:(\d+)/)||[])[1]||0),10); 277 var h = meta.height || parseInt(((cls.match(/\bh:(\d+)/)||[])[1]||0),10) || parseInt(((cls.match(/\bheight:(\d+)/)||[])[1]||0),10); 278 279 if (w) meta.width = w; 280 if (h) meta.height = h; 281 if (cls) meta.cls = cls; 282 283 // crank html5 style data attributes 284 var dataName = 'data-'; 285 for (var i=0; i < el.attributes.length; i++) { 286 a = el.attributes[i], n = $.trim(a.name); 287 var index = n.indexOf(dataName); 288 if (index === 0) { 289 n = n.substring(dataName.length); 290 meta[n] = a.value; 291 } 292 } 293 294 a = $.fn.media.defaults; 295 var b = options; 296 var c = meta; 297 298 var p = { params: { bgColor: options.bgColor || $.fn.media.defaults.bgColor } }; 299 var opts = $.extend({}, a, b, c); 300 $.each(['attrs','params','flashvars','silverlight'], function(i,o) { 301 opts[o] = $.extend({}, p[o] || {}, a[o] || {}, b[o] || {}, c[o] || {}); 302 }); 303 304 if (typeof opts.caption == 'undefined') opts.caption = $el.text(); 305 306 // make sure we have a source! 307 opts.src = opts.src || $el.attr('href') || $el.attr('src') || 'unknown'; 308 return opts; 309} 310 311// 312// Flash Player 313// 314 315// generate flash using SWFObject library if possible 316$.fn.media.swf = function(el, opts) { 317 var f, p; 318 if (!window.SWFObject && !window.swfobject) { 319 // roll our own 320 if (opts.flashvars) { 321 var a = [];
322 for (f in opts.flashvars) 323 a.push(f + '=' + opts.flashvars[f]); 324 if (!opts.params) opts.params = {}; 325 opts.params.flashvars = a.join('&'); 326 } 327 return generate(el, opts, 'flash'); 328 } 329 330 var id = el.id ? (' id="'+el.id+'"') : ''; 331 var cls = opts.cls ? (' class="' + opts.cls + '"') : ''; 332 var $div = $('<div' + id + cls + '>'); 333 334 // swfobject v2+ 335 if (window.swfobject) { 336 $(el).after($div).appendTo($div); 337 if (!el.id) el.id = 'movie_player_' + counter++; 338 339 // replace el with swfobject content 340 window.swfobject.embedSWF(opts.src, el.id, opts.width, opts.height, opts.flashVersion, 341 opts.expressInstaller, opts.flashvars, opts.params, opts.attrs); 342 } 343 // swfobject < v2 344 else { 345 $(el).after($div).remove(); 346 var so = new SWFObject(opts.src, 'movie_player_' + counter++, opts.width, opts.height, opts.flashVersion, opts.bgColor); 347 if (opts.expressInstaller) so.useExpressInstall(opts.expressInstaller); 348 349 for (p in opts.params) 350 if (p != 'bgColor') so.addParam(p, opts.params[p]); 351 for (f in opts.flashvars) 352 so.addVariable(f, opts.flashvars[f]); 353 so.write($div[0]); 354 } 355 356 if (opts.caption) $('<div>').appendTo($div).html(opts.caption); 357 return $div; 358}; 359 360// map flv and mp3 files to the swf player by default 361$.fn.media.flv = $.fn.media.mp3 = function(el, opts) { 362 var src = opts.src; 363 var player = /\.mp3\b/i.test(src) ? opts.mp3Player : opts.flvPlayer; 364 var key = opts.flvKeyName; 365 src = encodeURIComponent(src); 366 opts.src = player; 367 opts.src = opts.src + '?'+key+'=' + (src); 368 var srcObj = {}; 369 srcObj[key] = src; 370 opts.flashvars = $.extend({}, srcObj, opts.flashvars ); 371 return $.fn.media.swf(el, opts); 372}; 373 374// 375// Silverlight 376// 377$.fn.media.xaml = function(el, opts) { 378 if (!window.Sys || !window.Sys.Silverlight) { 379 if ($.fn.media.xaml.warning) return; 380 $.fn.media.xaml.warning = 1; 381 alert('You must include the Silverlight.js script.'); 382 return; 383 } 384 385 var props = { 386 width: opts.width, 387 height: opts.height, 388 background: opts.bgColor, 389 inplaceInstallPrompt: opts.silverlight.inplaceInstallPrompt, 390 isWindowless: opts.silverlight.isWindowless, 391 framerate: opts.silverlight.framerate, 392 version: opts.silverlight.version 393 }; 394 var events = { 395 onError: opts.silverlight.onError, 396 onLoad: opts.silverlight.onLoad 397 }; 398 399 var id1 = el.id ? (' id="'+el.id+'"') : ''; 400 var id2 = opts.id || 'AG' + counter++; 401 // convert element to div 402 var cls = opts.cls ? (' class="' + opts.cls + '"') : ''; 403 var $div = $('<div' + id1 + cls + '>'); 404 $(el).after($div).remove(); 405 406 Sys.Silverlight.createObjectEx({ 407 source: opts.src, 408 initParams: opts.silverlight.initParams, 409 userContext: opts.silverlight.userContext, 410 id: id2, 411 parentElement: $div[0], 412 properties: props, 413 events: events 414 }); 415 416 if (opts.caption) $('<div>').appendTo($div).html(opts.caption); 417 return $div; 418}; 419 420// 421// generate object/embed markup 422// 423function generate(el, opts, player) { 424 var $el = $(el); 425 var o = $.fn.media.defaults.players[player]; 426 var a, key, v; 427 428 if (player == 'iframe') { 429 o = $('<iframe' + ' width="' + opts.width + '" height="' + opts.height + '" >'); 430 o.attr('src', opts.src); 431 o.css('backgroundColor', o.bgColor); 432 } 433 else if (player == 'img') { 434 o = $('<img>'); 435 o.attr('src', opts.src); 436 if (opts.width) 437 o.attr('width', opts.width); 438 if (opts.height) 439 o.attr('height', opts.height); 440 o.css('backgroundColor', o.bgColor); 441 } 442 else if (lameIE) { 443 a = ['<object width="' + opts.width + '" height="' + opts.height + '" ']; 444 for (key in opts.attrs) 445 a.push(key + '="'+opts.attrs[key]+'" '); 446 for (key in o.ieAttrs || {}) { 447 v = o.ieAttrs[key]; 448 if (key == 'codebase' && window.location.protocol == 'https:') 449 v = v.replace('http','https'); 450 a.push(key + '="'+v+'" '); 451 } 452 a.push('></ob'+'ject'+'>'); 453 var p = ['<param name="' + (o.oUrl || 'src') +'" value="' + opts.src + '">']; 454 for (key in opts.params) 455 p.push('<param name="'+ key +'" value="' + opts.params[key] + '">'); 456 o = document.createElement(a.join(''));
457 for (var i=0; i < p.length; i++) 458 o.appendChild(document.createElement(p[i])); 459 } 460 else if (opts.standards) { 461 // Rewritten to be standards compliant by Richard Connamacher 462 a = ['<object type="' + o.mimetype +'" width="' + opts.width + '" height="' + opts.height +'"']; 463 if (opts.src) a.push(' data="' + opts.src + '" '); 464 if (msie) { 465 for (key in o.ieAttrs || {}) { 466 v = o.ieAttrs[key]; 467 if (key == 'codebase' && window.location.protocol == 'https:') 468 v = v.replace('http','https'); 469 a.push(key + '="'+v+'" '); 470 } 471 } 472 a.push('>'); 473 a.push('<param name="' + (o.oUrl || 'src') +'" value="' + opts.src + '">'); 474 for (key in opts.params) { 475 if (key == 'wmode' && player != 'flash') // FF3/Quicktime borks on wmode 476 continue; 477 a.push('<param name="'+ key +'" value="' + opts.params[key] + '">'); 478 } 479 // Alternate HTML 480 a.push('<div><p><strong>'+o.title+' Required</strong></p><p>'+o.title+' is required to view this media. <a href="'+o.pluginspage+'">Download Here</a>.</p></div>'); 481 a.push('</ob'+'ject'+'>'); 482 } 483 else { 484 a = ['<embed width="' + opts.width + '" height="' + opts.height + '" style="display:block"']; 485 if (opts.src) a.push(' src="' + opts.src + '" '); 486 for (key in opts.attrs) 487 a.push(key + '="'+opts.attrs[key]+'" '); 488 for (key in o.eAttrs || {}) 489 a.push(key + '="'+o.eAttrs[key]+'" '); 490 for (key in opts.params) { 491 if (key == 'wmode' && player != 'flash') // FF3/Quicktime borks on wmode 492 continue; 493 a.push(key + '="'+opts.params[key]+'" '); 494 } 495 a.push('></em'+'bed'+'>'); 496 } 497 // convert element to div 498 var id = el.id ? (' id="'+el.id+'"') : ''; 499 var cls = opts.cls ? (' class="' + opts.cls + '"') : ''; 500 var $div = $('<div' + id + cls + '>'); 501 $el.after($div).remove(); 502 if (lameIE || player == 'iframe' || player == 'img') 503 $div.append(o); 504 else 505 $div.html(a.join('')); 506 507 if (opts.caption) 508 $('<div>').appendTo($div).html(opts.caption); 509 return $div; 510} 511 512 513})(jQuery);
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.