mediaelement_rails 0.8.1 → 0.8.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +4 -0
- data/app/assets/javascripts/mediaelement_rails/mediaelement.js +175 -72
- data/app/assets/javascripts/mediaelement_rails/mediaelementplayer.js +288 -131
- data/app/assets/plugins/mediaelement_rails/flashmediaelement-cdn.swf +0 -0
- data/app/assets/plugins/mediaelement_rails/flashmediaelement.swf +0 -0
- data/app/assets/stylesheets/mediaelement_rails/mediaelementplayer.css.erb +22 -2
- data/lib/mediaelement_rails/version.rb +1 -1
- metadata +3 -3
@@ -12,6 +12,19 @@
|
|
12
12
|
*/
|
13
13
|
if (typeof jQuery != 'undefined') {
|
14
14
|
mejs.$ = jQuery;
|
15
|
+
} else if (typeof Zepto != 'undefined') {
|
16
|
+
mejs.$ = Zepto;
|
17
|
+
|
18
|
+
// define `outerWidth` method which has not been realized in Zepto
|
19
|
+
Zepto.fn.outerWidth = function(includeMargin) {
|
20
|
+
var width = $(this).width();
|
21
|
+
if (includeMargin) {
|
22
|
+
width += parseInt($(this).css('margin-right'), 10);
|
23
|
+
width += parseInt($(this).css('margin-left'), 10);
|
24
|
+
}
|
25
|
+
return width
|
26
|
+
}
|
27
|
+
|
15
28
|
} else if (typeof ender != 'undefined') {
|
16
29
|
mejs.$ = ender;
|
17
30
|
}
|
@@ -60,9 +73,25 @@ if (typeof jQuery != 'undefined') {
|
|
60
73
|
autoRewind: true,
|
61
74
|
// resize to media dimensions
|
62
75
|
enableAutosize: true,
|
76
|
+
|
77
|
+
/*
|
78
|
+
* Time format to use. Default: 'mm:ss'
|
79
|
+
* Supported units:
|
80
|
+
* h: hour
|
81
|
+
* m: minute
|
82
|
+
* s: second
|
83
|
+
* f: frame count
|
84
|
+
* When using 'hh', 'mm', 'ss' or 'ff' we always display 2 digits.
|
85
|
+
* If you use 'h', 'm', 's' or 'f' we display 1 digit if possible.
|
86
|
+
*
|
87
|
+
* Example to display 75 seconds:
|
88
|
+
* Format 'mm:ss': 01:15
|
89
|
+
* Format 'm:ss': 1:15
|
90
|
+
* Format 'm:s': 1:15
|
91
|
+
*/
|
92
|
+
timeFormat: '',
|
63
93
|
// forces the hour marker (##:00:00)
|
64
94
|
alwaysShowHours: false,
|
65
|
-
|
66
95
|
// show framecount in timecode (##:00:00:00)
|
67
96
|
showTimecodeFrameCount: false,
|
68
97
|
// used when showTimecodeFrameCount is set to true
|
@@ -102,9 +131,9 @@ if (typeof jQuery != 'undefined') {
|
|
102
131
|
],
|
103
132
|
action: function(player, media) {
|
104
133
|
if (media.paused || media.ended) {
|
105
|
-
|
134
|
+
media.play();
|
106
135
|
} else {
|
107
|
-
|
136
|
+
media.pause();
|
108
137
|
}
|
109
138
|
}
|
110
139
|
},
|
@@ -217,12 +246,13 @@ if (typeof jQuery != 'undefined') {
|
|
217
246
|
t.$media = t.$node = $(node);
|
218
247
|
t.node = t.media = t.$media[0];
|
219
248
|
|
249
|
+
if(!t.node) {
|
250
|
+
return
|
251
|
+
}
|
252
|
+
|
220
253
|
// check for existing player
|
221
254
|
if (typeof t.node.player != 'undefined') {
|
222
255
|
return t.node.player;
|
223
|
-
} else {
|
224
|
-
// attach player to DOM node for reference
|
225
|
-
t.node.player = t;
|
226
256
|
}
|
227
257
|
|
228
258
|
|
@@ -234,6 +264,19 @@ if (typeof jQuery != 'undefined') {
|
|
234
264
|
// extend default options
|
235
265
|
t.options = $.extend({},mejs.MepDefaults,o);
|
236
266
|
|
267
|
+
if (!t.options.timeFormat) {
|
268
|
+
// Generate the time format according to options
|
269
|
+
t.options.timeFormat = 'mm:ss';
|
270
|
+
if (t.options.alwaysShowHours) {
|
271
|
+
t.options.timeFormat = 'hh:mm:ss';
|
272
|
+
}
|
273
|
+
if (t.options.showTimecodeFrameCount) {
|
274
|
+
t.options.timeFormat += ':ff';
|
275
|
+
}
|
276
|
+
}
|
277
|
+
|
278
|
+
mejs.Utility.calculateTimeFormat(0, t.options, t.options.framesPerSecond || 25);
|
279
|
+
|
237
280
|
// unique ID
|
238
281
|
t.id = 'mep_' + mejs.mepIndex++;
|
239
282
|
|
@@ -351,6 +394,9 @@ if (typeof jQuery != 'undefined') {
|
|
351
394
|
// normal way of moving it into place (doesn't work on iOS)
|
352
395
|
t.container.find('.mejs-mediaelement').append(t.$media);
|
353
396
|
}
|
397
|
+
|
398
|
+
// needs to be assigned here, after iOS remap
|
399
|
+
t.node.player = t;
|
354
400
|
|
355
401
|
// find parts
|
356
402
|
t.controls = t.container.find('.mejs-controls');
|
@@ -743,6 +789,15 @@ if (typeof jQuery != 'undefined') {
|
|
743
789
|
t.setControlsSize();
|
744
790
|
}
|
745
791
|
}, false);
|
792
|
+
|
793
|
+
// Only change the time format when necessary
|
794
|
+
var duration = null;
|
795
|
+
t.media.addEventListener('timeupdate',function() {
|
796
|
+
if (duration !== this.duration) {
|
797
|
+
duration = this.duration;
|
798
|
+
mejs.Utility.calculateTimeFormat(duration, t.options, t.options.framesPerSecond || 25);
|
799
|
+
}
|
800
|
+
}, false);
|
746
801
|
|
747
802
|
t.container.focusout(function (e) {
|
748
803
|
if( e.relatedTarget ) { //FF is working on supporting focusout https://bugzilla.mozilla.org/show_bug.cgi?id=687787
|
@@ -823,7 +878,7 @@ if (typeof jQuery != 'undefined') {
|
|
823
878
|
}
|
824
879
|
|
825
880
|
// detect 100% mode - use currentStyle for IE since css() doesn't return percentages
|
826
|
-
if (t.height.toString().indexOf('%') > 0 || t.$node.css('max-width')
|
881
|
+
if (t.height.toString().indexOf('%') > 0 || (t.$node.css('max-width') !== 'none' && t.$node.css('max-width') !== 't.width') || (t.$node[0].currentStyle && t.$node[0].currentStyle.maxWidth === '100%')) {
|
827
882
|
|
828
883
|
// do we have the native dimensions yet?
|
829
884
|
var nativeWidth = (function() {
|
@@ -864,7 +919,7 @@ if (typeof jQuery != 'undefined') {
|
|
864
919
|
newHeight = parentHeight;
|
865
920
|
}
|
866
921
|
|
867
|
-
if (t.container.parent()[0].tagName.toLowerCase() === 'body') { // && t.container.siblings().count == 0) {
|
922
|
+
if (t.container.parent().length > 0 && t.container.parent()[0].tagName.toLowerCase() === 'body') { // && t.container.siblings().count == 0) {
|
868
923
|
parentWidth = $(window).width();
|
869
924
|
newHeight = $(window).height();
|
870
925
|
}
|
@@ -907,13 +962,6 @@ if (typeof jQuery != 'undefined') {
|
|
907
962
|
|
908
963
|
}
|
909
964
|
|
910
|
-
// special case for big play button so it doesn't go over the controls area
|
911
|
-
var playLayer = t.layers.find('.mejs-overlay-play'),
|
912
|
-
playButton = playLayer.find('.mejs-overlay-button');
|
913
|
-
|
914
|
-
playLayer.height(t.container.height() - t.controls.height());
|
915
|
-
playButton.css('margin-top', '-' + (playButton.height()/2 - t.controls.height()/2).toString() + 'px' );
|
916
|
-
|
917
965
|
},
|
918
966
|
|
919
967
|
setControlsSize: function() {
|
@@ -922,8 +970,6 @@ if (typeof jQuery != 'undefined') {
|
|
922
970
|
railWidth = 0,
|
923
971
|
rail = t.controls.find('.mejs-time-rail'),
|
924
972
|
total = t.controls.find('.mejs-time-total'),
|
925
|
-
current = t.controls.find('.mejs-time-current'),
|
926
|
-
loaded = t.controls.find('.mejs-time-loaded'),
|
927
973
|
others = rail.siblings(),
|
928
974
|
lastControl = others.last(),
|
929
975
|
lastControlPosition = null;
|
@@ -966,15 +1012,12 @@ if (typeof jQuery != 'undefined') {
|
|
966
1012
|
total.width(railWidth - (total.outerWidth(true) - total.width()));
|
967
1013
|
|
968
1014
|
if (lastControl.css('position') != 'absolute') {
|
969
|
-
lastControlPosition = lastControl.position();
|
1015
|
+
lastControlPosition = lastControl.length ? lastControl.position() : null;
|
970
1016
|
railWidth--;
|
971
1017
|
}
|
972
1018
|
} while (lastControlPosition !== null && lastControlPosition.top > 0 && railWidth > 0);
|
973
1019
|
|
974
|
-
|
975
|
-
t.setProgressRail();
|
976
|
-
if (t.setCurrentRail)
|
977
|
-
t.setCurrentRail();
|
1020
|
+
t.container.trigger('controlsresize');
|
978
1021
|
},
|
979
1022
|
|
980
1023
|
|
@@ -1015,7 +1058,7 @@ if (typeof jQuery != 'undefined') {
|
|
1015
1058
|
posterImg = posterDiv.find('img');
|
1016
1059
|
|
1017
1060
|
if (posterImg.length === 0) {
|
1018
|
-
posterImg = $('<img width="100%" height="100%" />').appendTo(posterDiv);
|
1061
|
+
posterImg = $('<img width="100%" height="100%" alt="" />').appendTo(posterDiv);
|
1019
1062
|
}
|
1020
1063
|
|
1021
1064
|
posterImg.attr('src', url);
|
@@ -1127,11 +1170,12 @@ if (typeof jQuery != 'undefined') {
|
|
1127
1170
|
}, false);
|
1128
1171
|
|
1129
1172
|
// error handling
|
1130
|
-
media.addEventListener('error',function() {
|
1173
|
+
media.addEventListener('error',function(e) {
|
1174
|
+
t.handleError(e);
|
1131
1175
|
loading.hide();
|
1132
|
-
|
1176
|
+
bigPlay.hide();
|
1133
1177
|
error.show();
|
1134
|
-
error.find('mejs-overlay-error').html("Error loading this resource");
|
1178
|
+
error.find('.mejs-overlay-error').html("Error loading this resource");
|
1135
1179
|
}, false);
|
1136
1180
|
|
1137
1181
|
media.addEventListener('keydown', function(e) {
|
@@ -1239,6 +1283,8 @@ if (typeof jQuery != 'undefined') {
|
|
1239
1283
|
},
|
1240
1284
|
remove: function() {
|
1241
1285
|
var t = this, featureIndex, feature;
|
1286
|
+
|
1287
|
+
t.container.prev('.mejs-offscreen').remove();
|
1242
1288
|
|
1243
1289
|
// invoke features cleanup
|
1244
1290
|
for (featureIndex in t.options.features) {
|
@@ -1284,6 +1330,15 @@ if (typeof jQuery != 'undefined') {
|
|
1284
1330
|
var t = this;
|
1285
1331
|
t.findTracks();
|
1286
1332
|
t.buildtracks(t, t.controls, t.layers, t.media);
|
1333
|
+
},
|
1334
|
+
resetSize: function(){
|
1335
|
+
var t = this;
|
1336
|
+
// webkit has trouble doing this without a delay
|
1337
|
+
setTimeout(function () {
|
1338
|
+
//
|
1339
|
+
t.setPlayerSize(t.width, t.height);
|
1340
|
+
t.setControlsSize();
|
1341
|
+
}, 50);
|
1287
1342
|
}
|
1288
1343
|
};
|
1289
1344
|
|
@@ -1433,9 +1488,9 @@ if (typeof jQuery != 'undefined') {
|
|
1433
1488
|
// STOP BUTTON
|
1434
1489
|
$.extend(MediaElementPlayer.prototype, {
|
1435
1490
|
buildstop: function(player, controls, layers, media) {
|
1436
|
-
var t = this
|
1437
|
-
|
1438
|
-
|
1491
|
+
var t = this;
|
1492
|
+
|
1493
|
+
$('<div class="mejs-button mejs-stop-button mejs-stop">' +
|
1439
1494
|
'<button type="button" aria-controls="' + t.id + '" title="' + t.options.stopText + '" aria-label="' + t.options.stopText + '"></button>' +
|
1440
1495
|
'</div>')
|
1441
1496
|
.appendTo(controls)
|
@@ -1448,8 +1503,8 @@ if (typeof jQuery != 'undefined') {
|
|
1448
1503
|
media.pause();
|
1449
1504
|
controls.find('.mejs-time-current').width('0px');
|
1450
1505
|
controls.find('.mejs-time-handle').css('left', '0px');
|
1451
|
-
controls.find('.mejs-time-float-current').html( mejs.Utility.secondsToTimeCode(0
|
1452
|
-
controls.find('.mejs-currenttime').html( mejs.Utility.secondsToTimeCode(0
|
1506
|
+
controls.find('.mejs-time-float-current').html( mejs.Utility.secondsToTimeCode(0, player.options));
|
1507
|
+
controls.find('.mejs-currenttime').html( mejs.Utility.secondsToTimeCode(0, player.options));
|
1453
1508
|
layers.find('.mejs-poster').show();
|
1454
1509
|
}
|
1455
1510
|
});
|
@@ -1472,15 +1527,16 @@ if (typeof jQuery != 'undefined') {
|
|
1472
1527
|
$('<div class="mejs-time-rail">' +
|
1473
1528
|
'<span class="mejs-time-total mejs-time-slider">' +
|
1474
1529
|
//'<span class="mejs-offscreen">' + this.options.progessHelpText + '</span>' +
|
1475
|
-
|
1476
|
-
|
1477
|
-
|
1478
|
-
|
1479
|
-
|
1480
|
-
|
1481
|
-
|
1530
|
+
'<span class="mejs-time-buffering"></span>' +
|
1531
|
+
'<span class="mejs-time-loaded"></span>' +
|
1532
|
+
'<span class="mejs-time-current"></span>' +
|
1533
|
+
'<span class="mejs-time-handle"></span>' +
|
1534
|
+
'<span class="mejs-time-float">' +
|
1535
|
+
'<span class="mejs-time-float-current">00:00</span>' +
|
1536
|
+
'<span class="mejs-time-float-corner"></span>' +
|
1537
|
+
'</span>' +
|
1482
1538
|
'</span>' +
|
1483
|
-
|
1539
|
+
'</div>')
|
1484
1540
|
.appendTo(controls);
|
1485
1541
|
controls.find('.mejs-time-buffering').hide();
|
1486
1542
|
|
@@ -1503,9 +1559,11 @@ if (typeof jQuery != 'undefined') {
|
|
1503
1559
|
x;
|
1504
1560
|
|
1505
1561
|
// mouse or touch position relative to the object
|
1506
|
-
if (e.originalEvent.changedTouches) {
|
1562
|
+
if (e.originalEvent && e.originalEvent.changedTouches) {
|
1507
1563
|
x = e.originalEvent.changedTouches[0].pageX;
|
1508
|
-
}else{
|
1564
|
+
} else if (e.changedTouches) { // for Zepto
|
1565
|
+
x = e.changedTouches[0].pageX;
|
1566
|
+
} else {
|
1509
1567
|
x = e.pageX;
|
1510
1568
|
}
|
1511
1569
|
|
@@ -1528,7 +1586,7 @@ if (typeof jQuery != 'undefined') {
|
|
1528
1586
|
// position floating time box
|
1529
1587
|
if (!mejs.MediaFeatures.hasTouch) {
|
1530
1588
|
timefloat.css('left', pos);
|
1531
|
-
timefloatcurrent.html( mejs.Utility.secondsToTimeCode(newTime) );
|
1589
|
+
timefloatcurrent.html( mejs.Utility.secondsToTimeCode(newTime, player.options) );
|
1532
1590
|
timefloat.show();
|
1533
1591
|
}
|
1534
1592
|
}
|
@@ -1543,7 +1601,7 @@ if (typeof jQuery != 'undefined') {
|
|
1543
1601
|
|
1544
1602
|
var seconds = media.currentTime,
|
1545
1603
|
timeSliderText = mejs.i18n.t('Time Slider'),
|
1546
|
-
time = mejs.Utility.secondsToTimeCode(seconds),
|
1604
|
+
time = mejs.Utility.secondsToTimeCode(seconds, player.options),
|
1547
1605
|
duration = media.duration;
|
1548
1606
|
|
1549
1607
|
slider.attr({
|
@@ -1678,6 +1736,10 @@ if (typeof jQuery != 'undefined') {
|
|
1678
1736
|
updateSlider(e);
|
1679
1737
|
}, false);
|
1680
1738
|
|
1739
|
+
t.container.on('controlsresize', function() {
|
1740
|
+
player.setProgressRail();
|
1741
|
+
player.setCurrentRail();
|
1742
|
+
});
|
1681
1743
|
|
1682
1744
|
// store for later use
|
1683
1745
|
t.loaded = loaded;
|
@@ -1694,8 +1756,8 @@ if (typeof jQuery != 'undefined') {
|
|
1694
1756
|
|
1695
1757
|
// newest HTML5 spec has buffered array (FF4, Webkit)
|
1696
1758
|
if (target && target.buffered && target.buffered.length > 0 && target.buffered.end && target.duration) {
|
1697
|
-
//
|
1698
|
-
percent = target.buffered.end(
|
1759
|
+
// account for a real array with multiple values - always read the end of the last buffer
|
1760
|
+
percent = target.buffered.end(target.buffered.length - 1) / target.duration;
|
1699
1761
|
}
|
1700
1762
|
// Some browsers (e.g., FF3.6 and Safari 5) cannot calculate target.bufferered.end()
|
1701
1763
|
// to be anything other than 0. If the byte count is available we use this instead.
|
@@ -1738,6 +1800,7 @@ if (typeof jQuery != 'undefined') {
|
|
1738
1800
|
}
|
1739
1801
|
});
|
1740
1802
|
})(mejs.$);
|
1803
|
+
|
1741
1804
|
(function($) {
|
1742
1805
|
|
1743
1806
|
// options
|
@@ -1754,8 +1817,7 @@ if (typeof jQuery != 'undefined') {
|
|
1754
1817
|
|
1755
1818
|
$('<div class="mejs-time" role="timer" aria-live="off">' +
|
1756
1819
|
'<span class="mejs-currenttime">' +
|
1757
|
-
|
1758
|
-
(player.options.showTimecodeFrameCount? '00:00:00':'00:00') +
|
1820
|
+
mejs.Utility.secondsToTimeCode(0, player.options) +
|
1759
1821
|
'</span>'+
|
1760
1822
|
'</div>')
|
1761
1823
|
.appendTo(controls);
|
@@ -1774,10 +1836,7 @@ if (typeof jQuery != 'undefined') {
|
|
1774
1836
|
if (controls.children().last().find('.mejs-currenttime').length > 0) {
|
1775
1837
|
$(t.options.timeAndDurationSeparator +
|
1776
1838
|
'<span class="mejs-duration">' +
|
1777
|
-
(t.options.duration
|
1778
|
-
mejs.Utility.secondsToTimeCode(t.options.duration, t.options.alwaysShowHours || t.media.duration > 3600, t.options.showTimecodeFrameCount, t.options.framesPerSecond || 25) :
|
1779
|
-
((player.options.alwaysShowHours ? '00:' : '') + (player.options.showTimecodeFrameCount? '00:00:00':'00:00'))
|
1780
|
-
) +
|
1839
|
+
mejs.Utility.secondsToTimeCode(t.options.duration, t.options) +
|
1781
1840
|
'</span>')
|
1782
1841
|
.appendTo(controls.find('.mejs-time'));
|
1783
1842
|
} else {
|
@@ -1787,10 +1846,7 @@ if (typeof jQuery != 'undefined') {
|
|
1787
1846
|
|
1788
1847
|
$('<div class="mejs-time mejs-duration-container">'+
|
1789
1848
|
'<span class="mejs-duration">' +
|
1790
|
-
(t.options.duration
|
1791
|
-
mejs.Utility.secondsToTimeCode(t.options.duration, t.options.alwaysShowHours || t.media.duration > 3600, t.options.showTimecodeFrameCount, t.options.framesPerSecond || 25) :
|
1792
|
-
((player.options.alwaysShowHours ? '00:' : '') + (player.options.showTimecodeFrameCount? '00:00:00':'00:00'))
|
1793
|
-
) +
|
1849
|
+
mejs.Utility.secondsToTimeCode(t.options.duration, t.options) +
|
1794
1850
|
'</span>' +
|
1795
1851
|
'</div>')
|
1796
1852
|
.appendTo(controls);
|
@@ -1807,7 +1863,7 @@ if (typeof jQuery != 'undefined') {
|
|
1807
1863
|
var t = this;
|
1808
1864
|
|
1809
1865
|
if (t.currenttime) {
|
1810
|
-
t.currenttime.html(mejs.Utility.secondsToTimeCode(t.media.currentTime, t.options
|
1866
|
+
t.currenttime.html(mejs.Utility.secondsToTimeCode(t.media.currentTime, t.options));
|
1811
1867
|
}
|
1812
1868
|
},
|
1813
1869
|
|
@@ -1818,7 +1874,7 @@ if (typeof jQuery != 'undefined') {
|
|
1818
1874
|
t.container.toggleClass("mejs-long-video", t.media.duration > 3600);
|
1819
1875
|
|
1820
1876
|
if (t.durationD && (t.options.duration > 0 || t.media.duration)) {
|
1821
|
-
t.durationD.html(mejs.Utility.secondsToTimeCode(t.options.duration > 0 ? t.options.duration : t.media.duration, t.options
|
1877
|
+
t.durationD.html(mejs.Utility.secondsToTimeCode(t.options.duration > 0 ? t.options.duration : t.media.duration, t.options));
|
1822
1878
|
}
|
1823
1879
|
}
|
1824
1880
|
});
|
@@ -1898,8 +1954,10 @@ if (typeof jQuery != 'undefined') {
|
|
1898
1954
|
// ajust mute button style
|
1899
1955
|
if (volume === 0) {
|
1900
1956
|
mute.removeClass('mejs-mute').addClass('mejs-unmute');
|
1957
|
+
mute.children('button').attr('title', mejs.i18n.t('Unmute')).attr('aria-label', mejs.i18n.t('Unmute'));
|
1901
1958
|
} else {
|
1902
1959
|
mute.removeClass('mejs-unmute').addClass('mejs-mute');
|
1960
|
+
mute.children('button').attr('title', mejs.i18n.t('Mute')).attr('aria-label', mejs.i18n.t('Mute'));
|
1903
1961
|
}
|
1904
1962
|
|
1905
1963
|
// top/left of full size volume slider background
|
@@ -1945,7 +2003,6 @@ if (typeof jQuery != 'undefined') {
|
|
1945
2003
|
|
1946
2004
|
var
|
1947
2005
|
railHeight = volumeTotal.height(),
|
1948
|
-
totalTop = parseInt(volumeTotal.css('top').replace(/px/,''),10),
|
1949
2006
|
newY = e.pageY - totalOffset.top;
|
1950
2007
|
|
1951
2008
|
volume = (railHeight - newY) / railHeight;
|
@@ -2078,25 +2135,25 @@ if (typeof jQuery != 'undefined') {
|
|
2078
2135
|
}
|
2079
2136
|
updateVolumeSlider(e);
|
2080
2137
|
}, false);
|
2081
|
-
|
2082
|
-
if
|
2083
|
-
|
2084
|
-
|
2085
|
-
|
2086
|
-
// mutes the media and sets the volume icon muted if the initial volume is set to 0
|
2087
|
-
if (player.options.startVolume === 0) {
|
2088
|
-
media.setMuted(true);
|
2089
|
-
}
|
2090
|
-
|
2091
|
-
// shim gets the startvolume as a parameter, but we have to set it on the native <video> and <audio> elements
|
2092
|
-
if (media.pluginType === 'native') {
|
2093
|
-
media.setVolume(player.options.startVolume);
|
2094
|
-
}
|
2138
|
+
|
2139
|
+
// mutes the media and sets the volume icon muted if the initial volume is set to 0
|
2140
|
+
if (player.options.startVolume === 0) {
|
2141
|
+
media.setMuted(true);
|
2095
2142
|
}
|
2143
|
+
|
2144
|
+
// shim gets the startvolume as a parameter, but we have to set it on the native <video> and <audio> elements
|
2145
|
+
if (media.pluginType === 'native') {
|
2146
|
+
media.setVolume(player.options.startVolume);
|
2147
|
+
}
|
2148
|
+
|
2149
|
+
t.container.on('controlsresize', function() {
|
2150
|
+
positionVolumeHandle(media.volume);
|
2151
|
+
});
|
2096
2152
|
}
|
2097
2153
|
});
|
2098
2154
|
|
2099
2155
|
})(mejs.$);
|
2156
|
+
|
2100
2157
|
(function($) {
|
2101
2158
|
|
2102
2159
|
$.extend(mejs.MepDefaults, {
|
@@ -2143,9 +2200,6 @@ if (typeof jQuery != 'undefined') {
|
|
2143
2200
|
}
|
2144
2201
|
|
2145
2202
|
var t = this,
|
2146
|
-
normalHeight = 0,
|
2147
|
-
normalWidth = 0,
|
2148
|
-
container = player.container,
|
2149
2203
|
fullscreenBtn =
|
2150
2204
|
$('<div class="mejs-button mejs-fullscreen-button">' +
|
2151
2205
|
'<button type="button" aria-controls="' + t.id + '" title="' + t.options.fullscreenText + '" aria-label="' + t.options.fullscreenText + '"></button>' +
|
@@ -2375,6 +2429,9 @@ if (typeof jQuery != 'undefined') {
|
|
2375
2429
|
player.exitFullScreen();
|
2376
2430
|
}
|
2377
2431
|
});
|
2432
|
+
|
2433
|
+
t.normalHeight = 0;
|
2434
|
+
t.normalWidth = 0;
|
2378
2435
|
|
2379
2436
|
},
|
2380
2437
|
|
@@ -2399,8 +2456,8 @@ if (typeof jQuery != 'undefined') {
|
|
2399
2456
|
$(document.documentElement).addClass('mejs-fullscreen');
|
2400
2457
|
|
2401
2458
|
// store sizing
|
2402
|
-
normalHeight = t.container.height();
|
2403
|
-
normalWidth = t.container.width();
|
2459
|
+
t.normalHeight = t.container.height();
|
2460
|
+
t.normalWidth = t.container.width();
|
2404
2461
|
|
2405
2462
|
// attempt to do true fullscreen (Safari 5.1 and Firefox Nightly only for now)
|
2406
2463
|
if (t.media.pluginType === 'native') {
|
@@ -2415,13 +2472,25 @@ if (typeof jQuery != 'undefined') {
|
|
2415
2472
|
setTimeout(function checkFullscreen() {
|
2416
2473
|
|
2417
2474
|
if (t.isNativeFullScreen) {
|
2418
|
-
var zoomMultiplier = window["devicePixelRatio"] || 1
|
2475
|
+
var zoomMultiplier = window["devicePixelRatio"] || 1,
|
2419
2476
|
// Use a percent error margin since devicePixelRatio is a float and not exact.
|
2420
|
-
|
2421
|
-
|
2422
|
-
|
2423
|
-
|
2424
|
-
|
2477
|
+
percentErrorMargin = 0.002, // 0.2%
|
2478
|
+
windowWidth = zoomMultiplier * $(window).width(),
|
2479
|
+
screenWidth = screen.width,
|
2480
|
+
// ** 13twelve
|
2481
|
+
// Screen width is sort of useless: http://www.quirksmode.org/blog/archives/2013/11/screenwidth_is.html
|
2482
|
+
// My rMBP ignores devicePixelRatio when returning the values, so fullscreen would always fail the "suddenly not fullscreen" test
|
2483
|
+
// Theory: the gap between reported values should give us an indication of browser behavior with screen.width and devicePixelRatio
|
2484
|
+
zoomedWindowWidth = zoomMultiplier * windowWidth;
|
2485
|
+
|
2486
|
+
if (Math.abs(screenWidth-windowWidth) > Math.abs(screenWidth-zoomedWindowWidth)) {
|
2487
|
+
// screen.width is likely true pixels, not CSS pixels, so we need to use the zoomed window width for comparison
|
2488
|
+
windowWidth = zoomedWindowWidth;
|
2489
|
+
}
|
2490
|
+
// ** / 13twelve
|
2491
|
+
|
2492
|
+
var absDiff = Math.abs(screenWidth - windowWidth),
|
2493
|
+
marginError = screenWidth * percentErrorMargin;
|
2425
2494
|
|
2426
2495
|
// check if the video is suddenly not really fullscreen
|
2427
2496
|
if (absDiff > marginError) {
|
@@ -2432,9 +2501,8 @@ if (typeof jQuery != 'undefined') {
|
|
2432
2501
|
setTimeout(checkFullscreen, 500);
|
2433
2502
|
}
|
2434
2503
|
}
|
2435
|
-
|
2436
|
-
|
2437
|
-
}, 500);
|
2504
|
+
|
2505
|
+
}, 1000);
|
2438
2506
|
}
|
2439
2507
|
|
2440
2508
|
} else if (mejs.MediaFeatures.hasSemiNativeFullScreen) {
|
@@ -2516,6 +2584,8 @@ if (typeof jQuery != 'undefined') {
|
|
2516
2584
|
|
2517
2585
|
t.container.find('.mejs-captions-text').css('font-size', screen.width / t.width * 1.00 * 100 + '%');
|
2518
2586
|
t.container.find('.mejs-captions-position').css('bottom', '45px');
|
2587
|
+
|
2588
|
+
t.container.trigger('enteredfullscreen');
|
2519
2589
|
},
|
2520
2590
|
|
2521
2591
|
exitFullScreen: function() {
|
@@ -2542,25 +2612,24 @@ if (typeof jQuery != 'undefined') {
|
|
2542
2612
|
|
2543
2613
|
t.container
|
2544
2614
|
.removeClass('mejs-container-fullscreen')
|
2545
|
-
.width(normalWidth)
|
2546
|
-
.height(normalHeight);
|
2547
|
-
//.css({position: '', left: '', top: '', right: '', bottom: '', overflow: 'inherit', width: normalWidth + 'px', height: normalHeight + 'px', 'z-index': 1});
|
2615
|
+
.width(t.normalWidth)
|
2616
|
+
.height(t.normalHeight);
|
2548
2617
|
|
2549
2618
|
if (t.media.pluginType === 'native') {
|
2550
2619
|
t.$media
|
2551
|
-
.width(normalWidth)
|
2552
|
-
.height(normalHeight);
|
2620
|
+
.width(t.normalWidth)
|
2621
|
+
.height(t.normalHeight);
|
2553
2622
|
} else {
|
2554
2623
|
t.container.find('.mejs-shim')
|
2555
|
-
.width(normalWidth)
|
2556
|
-
.height(normalHeight);
|
2624
|
+
.width(t.normalWidth)
|
2625
|
+
.height(t.normalHeight);
|
2557
2626
|
|
2558
|
-
t.media.setVideoSize(normalWidth, normalHeight);
|
2627
|
+
t.media.setVideoSize(t.normalWidth, t.normalHeight);
|
2559
2628
|
}
|
2560
2629
|
|
2561
2630
|
t.layers.children('div')
|
2562
|
-
.width(normalWidth)
|
2563
|
-
.height(normalHeight);
|
2631
|
+
.width(t.normalWidth)
|
2632
|
+
.height(t.normalHeight);
|
2564
2633
|
|
2565
2634
|
t.fullscreenBtn
|
2566
2635
|
.removeClass('mejs-unfullscreen')
|
@@ -2571,6 +2640,8 @@ if (typeof jQuery != 'undefined') {
|
|
2571
2640
|
|
2572
2641
|
t.container.find('.mejs-captions-text').css('font-size','');
|
2573
2642
|
t.container.find('.mejs-captions-position').css('bottom', '');
|
2643
|
+
|
2644
|
+
t.container.trigger('exitedfullscreen');
|
2574
2645
|
}
|
2575
2646
|
});
|
2576
2647
|
|
@@ -2581,6 +2652,8 @@ if (typeof jQuery != 'undefined') {
|
|
2581
2652
|
// Speed
|
2582
2653
|
$.extend(mejs.MepDefaults, {
|
2583
2654
|
|
2655
|
+
// We also support to pass object like this:
|
2656
|
+
// [{name: 'Slow', value: '0.75'}, {name: 'Normal', value: '1.00'}, ...]
|
2584
2657
|
speeds: ['2.00', '1.50', '1.25', '1.00', '0.75'],
|
2585
2658
|
|
2586
2659
|
defaultSpeed: '1.00',
|
@@ -2599,53 +2672,90 @@ if (typeof jQuery != 'undefined') {
|
|
2599
2672
|
speedButton = null,
|
2600
2673
|
speedSelector = null,
|
2601
2674
|
playbackSpeed = null,
|
2602
|
-
|
2603
|
-
|
2604
|
-
|
2605
|
-
|
2606
|
-
|
2607
|
-
|
2608
|
-
|
2675
|
+
inputId = null;
|
2676
|
+
|
2677
|
+
var speeds = [];
|
2678
|
+
var defaultInArray = false;
|
2679
|
+
for (var i=0, len=t.options.speeds.length; i < len; i++) {
|
2680
|
+
var s = t.options.speeds[i];
|
2681
|
+
if (typeof(s) === 'string'){
|
2682
|
+
speeds.push({
|
2683
|
+
name: s + t.options.speedChar,
|
2684
|
+
value: s
|
2685
|
+
});
|
2686
|
+
if(s === t.options.defaultSpeed) {
|
2687
|
+
defaultInArray = true;
|
2688
|
+
}
|
2689
|
+
}
|
2690
|
+
else {
|
2691
|
+
speeds.push(s);
|
2692
|
+
if(s.value === t.options.defaultSpeed) {
|
2693
|
+
defaultInArray = true;
|
2694
|
+
}
|
2695
|
+
}
|
2696
|
+
}
|
2697
|
+
|
2698
|
+
if (!defaultInArray) {
|
2699
|
+
speeds.push({
|
2700
|
+
name: t.options.defaultSpeed + t.options.speedChar,
|
2701
|
+
value: t.options.defaultSpeed
|
2702
|
+
});
|
2609
2703
|
}
|
2610
2704
|
|
2611
|
-
|
2612
|
-
return parseFloat(b) - parseFloat(a);
|
2705
|
+
speeds.sort(function(a, b) {
|
2706
|
+
return parseFloat(b.value) - parseFloat(a.value);
|
2613
2707
|
});
|
2614
2708
|
|
2615
|
-
|
2709
|
+
var getSpeedNameFromValue = function(value) {
|
2710
|
+
for(i=0,len=speeds.length; i <len; i++) {
|
2711
|
+
if (speeds[i].value === value) {
|
2712
|
+
return speeds[i].name;
|
2713
|
+
}
|
2714
|
+
}
|
2715
|
+
};
|
2716
|
+
|
2717
|
+
var html = '<div class="mejs-button mejs-speed-button">' +
|
2718
|
+
'<button type="button">' + getSpeedNameFromValue(t.options.defaultSpeed) + '</button>' +
|
2719
|
+
'<div class="mejs-speed-selector">' +
|
2720
|
+
'<ul>';
|
2721
|
+
|
2722
|
+
for (i = 0, il = speeds.length; i<il; i++) {
|
2723
|
+
inputId = t.id + '-speed-' + speeds[i].value;
|
2616
2724
|
html += '<li>' +
|
2617
2725
|
'<input type="radio" name="speed" ' +
|
2618
|
-
'value="' +
|
2619
|
-
'id="' +
|
2620
|
-
(
|
2726
|
+
'value="' + speeds[i].value + '" ' +
|
2727
|
+
'id="' + inputId + '" ' +
|
2728
|
+
(speeds[i].value === t.options.defaultSpeed ? ' checked' : '') +
|
2621
2729
|
' />' +
|
2622
|
-
'<label for="' +
|
2623
|
-
(
|
2624
|
-
'>' +
|
2730
|
+
'<label for="' + inputId + '" ' +
|
2731
|
+
(speeds[i].value === t.options.defaultSpeed ? ' class="mejs-speed-selected"' : '') +
|
2732
|
+
'>' + speeds[i].name + '</label>' +
|
2625
2733
|
'</li>';
|
2626
2734
|
}
|
2627
2735
|
html += '</ul></div></div>';
|
2628
2736
|
|
2629
2737
|
speedButton = $(html).appendTo(controls);
|
2630
|
-
speedSelector = speedButton.find('.mejs-speed-selector');
|
2738
|
+
speedSelector = speedButton.find('.mejs-speed-selector');
|
2631
2739
|
|
2632
|
-
|
2740
|
+
playbackSpeed = t.options.defaultSpeed;
|
2633
2741
|
|
2634
2742
|
speedSelector
|
2635
2743
|
.on('click', 'input[type="radio"]', function() {
|
2636
2744
|
var newSpeed = $(this).attr('value');
|
2637
|
-
|
2745
|
+
playbackSpeed = newSpeed;
|
2638
2746
|
media.playbackRate = parseFloat(newSpeed);
|
2639
|
-
speedButton.find('button').html(newSpeed
|
2747
|
+
speedButton.find('button').html(getSpeedNameFromValue(newSpeed));
|
2640
2748
|
speedButton.find('.mejs-speed-selected').removeClass('mejs-speed-selected');
|
2641
2749
|
speedButton.find('input[type="radio"]:checked').next().addClass('mejs-speed-selected');
|
2642
2750
|
});
|
2643
|
-
|
2644
|
-
|
2645
|
-
|
2646
|
-
|
2647
|
-
|
2648
|
-
|
2751
|
+
speedButton
|
2752
|
+
.one( 'mouseenter focusin', function() {
|
2753
|
+
speedSelector
|
2754
|
+
.height(
|
2755
|
+
speedButton.find('.mejs-speed-selector ul').outerHeight(true) +
|
2756
|
+
speedButton.find('.mejs-speed-translations').outerHeight(true))
|
2757
|
+
.css('top', (-1 * speedSelector.height()) + 'px');
|
2758
|
+
});
|
2649
2759
|
}
|
2650
2760
|
}
|
2651
2761
|
});
|
@@ -2661,6 +2771,10 @@ if (typeof jQuery != 'undefined') {
|
|
2661
2771
|
|
2662
2772
|
tracksText: mejs.i18n.t('Captions/Subtitles'),
|
2663
2773
|
|
2774
|
+
// By default, no WAI-ARIA live region - don't make a
|
2775
|
+
// screen reader speak captions over an audio track.
|
2776
|
+
tracksAriaLive: false,
|
2777
|
+
|
2664
2778
|
// option to remove the [cc] button when no <track kind="subtitles"> are present
|
2665
2779
|
hideCaptionsButtonWhenEmpty: true,
|
2666
2780
|
|
@@ -2688,8 +2802,9 @@ if (typeof jQuery != 'undefined') {
|
|
2688
2802
|
return;
|
2689
2803
|
|
2690
2804
|
var t = this,
|
2691
|
-
|
2692
|
-
|
2805
|
+
attr = t.options.tracksAriaLive ?
|
2806
|
+
'role="log" aria-live="assertive" aria-atomic="false"' : '',
|
2807
|
+
i;
|
2693
2808
|
|
2694
2809
|
if (t.domNode.textTracks) { // if browser will do native captions, prefer mejs captions, loop through tracks and hide
|
2695
2810
|
for (i = t.domNode.textTracks.length - 1; i >= 0; i--) {
|
@@ -2701,7 +2816,8 @@ if (typeof jQuery != 'undefined') {
|
|
2701
2816
|
$('<div class="mejs-chapters mejs-layer"></div>')
|
2702
2817
|
.prependTo(layers).hide();
|
2703
2818
|
player.captions =
|
2704
|
-
$('<div class="mejs-captions-layer mejs-layer"><div class="mejs-captions-position mejs-captions-position-hover"
|
2819
|
+
$('<div class="mejs-captions-layer mejs-layer"><div class="mejs-captions-position mejs-captions-position-hover" ' +
|
2820
|
+
attr + '><span class="mejs-captions-text"></span></div></div>')
|
2705
2821
|
.prependTo(layers).hide();
|
2706
2822
|
player.captionsText = player.captions.find('.mejs-captions-text');
|
2707
2823
|
player.captionsButton =
|
@@ -2821,6 +2937,10 @@ if (typeof jQuery != 'undefined') {
|
|
2821
2937
|
}
|
2822
2938
|
});
|
2823
2939
|
|
2940
|
+
t.container.on('controlsresize', function() {
|
2941
|
+
t.adjustLanguageBox();
|
2942
|
+
});
|
2943
|
+
|
2824
2944
|
// check for autoplay
|
2825
2945
|
if (player.node.getAttribute('autoplay') !== null) {
|
2826
2946
|
player.chapters.css('visibility','hidden');
|
@@ -2872,8 +2992,6 @@ if (typeof jQuery != 'undefined') {
|
|
2872
2992
|
|
2873
2993
|
track.isLoaded = true;
|
2874
2994
|
|
2875
|
-
// create button
|
2876
|
-
//t.addTrackButton(track.srclang);
|
2877
2995
|
t.enableTrackButton(track.srclang, track.label);
|
2878
2996
|
|
2879
2997
|
t.loadNextTrack();
|
@@ -2908,6 +3026,7 @@ if (typeof jQuery != 'undefined') {
|
|
2908
3026
|
}
|
2909
3027
|
},
|
2910
3028
|
error: function() {
|
3029
|
+
t.removeTrackButton(track.srclang);
|
2911
3030
|
t.loadNextTrack();
|
2912
3031
|
}
|
2913
3032
|
});
|
@@ -2933,6 +3052,14 @@ if (typeof jQuery != 'undefined') {
|
|
2933
3052
|
|
2934
3053
|
t.adjustLanguageBox();
|
2935
3054
|
},
|
3055
|
+
|
3056
|
+
removeTrackButton: function(lang) {
|
3057
|
+
var t = this;
|
3058
|
+
|
3059
|
+
t.captionsButton.find('input[value=' + lang + ']').closest('li').remove();
|
3060
|
+
|
3061
|
+
t.adjustLanguageBox();
|
3062
|
+
},
|
2936
3063
|
|
2937
3064
|
addTrackButton: function(lang, label) {
|
2938
3065
|
var t = this;
|
@@ -2970,7 +3097,7 @@ if (typeof jQuery != 'undefined') {
|
|
2970
3097
|
// check if any subtitles
|
2971
3098
|
if (t.options.hideCaptionsButtonWhenEmpty) {
|
2972
3099
|
for (i=0; i<t.tracks.length; i++) {
|
2973
|
-
if (t.tracks[i].kind == 'subtitles') {
|
3100
|
+
if (t.tracks[i].kind == 'subtitles' && t.tracks[i].isLoaded) {
|
2974
3101
|
hasSubtitles = true;
|
2975
3102
|
break;
|
2976
3103
|
}
|
@@ -3116,7 +3243,7 @@ if (typeof jQuery != 'undefined') {
|
|
3116
3243
|
'<div class="mejs-chapter" rel="' + chapters.entries.times[i].start + '" style="left: ' + usedPercent.toString() + '%;width: ' + percent.toString() + '%;">' +
|
3117
3244
|
'<div class="mejs-chapter-block' + ((i==chapters.entries.times.length-1) ? ' mejs-chapter-block-last' : '') + '">' +
|
3118
3245
|
'<span class="ch-title">' + chapters.entries.text[i] + '</span>' +
|
3119
|
-
'<span class="ch-time">' + mejs.Utility.secondsToTimeCode(chapters.entries.times[i].start) + '–' + mejs.Utility.secondsToTimeCode(chapters.entries.times[i].stop) + '</span>' +
|
3246
|
+
'<span class="ch-time">' + mejs.Utility.secondsToTimeCode(chapters.entries.times[i].start, t.options) + '–' + mejs.Utility.secondsToTimeCode(chapters.entries.times[i].stop, t.options) + '</span>' +
|
3120
3247
|
'</div>' +
|
3121
3248
|
'</div>'));
|
3122
3249
|
usedPercent += percent;
|
@@ -3266,8 +3393,6 @@ if (typeof jQuery != 'undefined') {
|
|
3266
3393
|
lines = container.find("p"),
|
3267
3394
|
styleNode = trackText.find("#" + container.attr("style")),
|
3268
3395
|
styles,
|
3269
|
-
begin,
|
3270
|
-
end,
|
3271
3396
|
text,
|
3272
3397
|
entries = {text:[], times:[]};
|
3273
3398
|
|
@@ -3536,6 +3661,38 @@ $.extend(mejs.MepDefaults,
|
|
3536
3661
|
});
|
3537
3662
|
|
3538
3663
|
})(mejs.$);
|
3664
|
+
(function($) {
|
3665
|
+
// skip back button
|
3666
|
+
|
3667
|
+
$.extend(mejs.MepDefaults, {
|
3668
|
+
skipBackInterval: 30,
|
3669
|
+
// %1 will be replaced with skipBackInterval in this string
|
3670
|
+
skipBackText: mejs.i18n.t('Skip back %1 seconds')
|
3671
|
+
});
|
3672
|
+
|
3673
|
+
$.extend(MediaElementPlayer.prototype, {
|
3674
|
+
buildskipback: function(player, controls, layers, media) {
|
3675
|
+
var
|
3676
|
+
t = this,
|
3677
|
+
// Replace %1 with skip back interval
|
3678
|
+
backText = t.options.skipBackText.replace('%1', t.options.skipBackInterval),
|
3679
|
+
// create the loop button
|
3680
|
+
loop =
|
3681
|
+
$('<div class="mejs-button mejs-skip-back-button">' +
|
3682
|
+
'<button type="button" aria-controls="' + t.id + '" title="' + backText + '" aria-label="' + backText + '">' + t.options.skipBackInterval + '</button>' +
|
3683
|
+
'</div>')
|
3684
|
+
// append it to the toolbar
|
3685
|
+
.appendTo(controls)
|
3686
|
+
// add a click toggle event
|
3687
|
+
.click(function() {
|
3688
|
+
media.setCurrentTime(Math.max(media.currentTime - t.options.skipBackInterval, 0));
|
3689
|
+
$(this).find('button').blur();
|
3690
|
+
});
|
3691
|
+
}
|
3692
|
+
});
|
3693
|
+
|
3694
|
+
})(mejs.$);
|
3695
|
+
|
3539
3696
|
/**
|
3540
3697
|
* Postroll plugin
|
3541
3698
|
*/
|