1/* 2 AUTHOR: Osvaldas Valutis, www.osvaldas.info 3*/ 4 5 6 7;(function( $, window, document, undefined ) 8{ 9 var isTouch = 'ontouchstart' in window, 10 eStart = isTouch ? 'touchstart' : 'mousedown', 11 eMove = isTouch ? 'touchmove' : 'mousemove', 12 eEnd = isTouch ? 'touchend' : 'mouseup', 13 eCancel = isTouch ? 'touchcancel' : 'mouseup', 14 secondsToTime = function( secs ) 15 { 16 var hours = Math.floor( secs / 3600 ), minutes = Math.floor( secs % 3600 / 60 ), seconds = Math.ceil( secs % 3600 % 60 ); 17 return ( hours == 0 ? '' : hours > 0 && hours.toString().length < 2 ? '0'+hours+':' : hours+':' ) + ( minutes.toString().length < 2 ? '0'+minutes : minutes ) + ':' + ( seconds.toString().length < 2 ? '0'+seconds : seconds ); 18 }, 19 canPlayType = function( file ) 20 { 21 var audioElement = document.createElement( 'audio' ); 22 return !!( audioElement.canPlayType && audioElement.canPlayType( 'audio/' + file.split( '.' ).pop().toLowerCase() + ';' ).replace( /no/, '' ) ); 23 }; 24 25 $.fn.audioPlayer = function( params ) 26 { 27 var params = $.extend( { classPrefix: 'audioplayer', strPlay: 'Play', strPause: 'Pause', strVolume: 'Volume' }, params ), 28 cssClass = {}, 29 cssClassSub = 30 { 31 playPause: 'playpause', 32 playing: 'playing', 33 time: 'time', 34 timeCurrent: 'time-current', 35 timeDuration: 'time-duration', 36 bar: 'bar', 37 barLoaded: 'bar-loaded', 38 barPlayed: 'bar-played', 39 barPlayedPoint: 'bar-point', 40 barTime: 'bar-time', 41 volume: 'volume', 42 volumeButton: 'volume-button', 43 volumeAdjust: 'volume-adjust', 44 noVolume: 'novolume', 45 mute: 'mute', 46 mini: 'mini', 47 download: 'download' 48 }; 49 50 for( var subName in cssClassSub ) 51 cssClass[ subName ] = params.classPrefix + '-' + cssClassSub[ subName ]; 52 53 this.each( function() 54 { 55 if( $( this ).prop( 'tagName' ).toLowerCase() != 'audio' ) 56 return false; 57 58 var $this = $( this ), 59 audioFile = $this.attr( 'src' ), 60 isAutoPlay = $this.get( 0 ).getAttribute( 'autoplay' ), isAutoPlay = isAutoPlay === '' || isAutoPlay === 'autoplay' ? true : false, 61 isLoop = $this.get( 0 ).getAttribute( 'loop' ), isLoop = isLoop === '' || isLoop === 'loop' ? true : false, 62 isSupport = false; 63 64 if( typeof audioFile === 'undefined' ) 65 { 66 $this.find( 'source' ).each( function() 67 { 68 audioFile = $( this ).attr( 'src' ); 69 if( typeof audioFile !== 'undefined' && canPlayType( audioFile ) ) 70 { 71 isSupport = true; 72 return false; 73 } 74 }); 75 } 76 else if( canPlayType( audioFile ) ) isSupport = true; 77 78 var thePlayer = $( '<div class="' + params.classPrefix + '">' + ( isSupport ? $( '<div>' ).append( $this.eq( 0 ).clone() ).html() : '<embed src="' + audioFile + '" width="0" height="0" volume="100" autostart="' + isAutoPlay.toString() +'" loop="' + isLoop.toString() + '" />' ) + '<div class="' + cssClass.playPause + '" title="' + params.strPlay + '"><a href="#">' + params.strPlay + '</a></div></div>' ), 79 theAudio = isSupport ? thePlayer.find( 'audio' ) : thePlayer.find( 'embed' ), theAudio = theAudio.get( 0 ); 80 theDuration = thePlayer.find( 'audio' ).attr('data-duration'); 81 theLink = thePlayer.find( 'audio' ).find('source').attr('src'); 82 83 if( isSupport ) 84 { 85 thePlayer.find( 'audio' ).css( { 'width': 0, 'height': 0, 'visibility': 'hidden' } ); 86 //thePlayer.append( '<div class="' + cssClass.time + '"><span class="'+cssClass.timeCurrent+'"></span>' + '/' + theDuration +'</div><div class="' + cssClass.bar + '"><div class="' + cssClass.barLoaded + '"></div><div class="' + cssClass.barPlayed + '"><div class="' + cssClass.barPlayedPoint + '"></div></div></div><div class="' + cssClass.time + ' ' + cssClass.timeDuration + '"></div><div class="' + cssClass.volume + '"><div class="' + cssClass.volumeButton + '" title="' + params.strVolume + '"><a href="#">' + params.strVolume + '</a></div><div class="' + cssClass.volumeAdjust + '"><div><div></div></div></div></div><a href="'+theLink+'" class="'+cssClass.download+'" download></a>' ); 87 thePlayer.append( '<div class="' + cssClass.bar + '"><div class="' + cssClass.barLoaded + '"></div><div class="' + cssClass.barPlayed + '"><div class="' + cssClass.barPlayedPoint + '"></div></div></div><div class="' + cssClass.time + ' ' + cssClass.timeDuration + '"></div>
87<div class="' + cssClass.volume + '"><div class="' + cssClass.volumeButton + '" title="' + params.strVolume + '"><a href="#">' + params.strVolume + '</a></div><div class="' + cssClass.time + '">' + theDuration +'</div><div class="' + cssClass.volumeAdjust + '"><div><div></div></div></div></div><a href="'+theLink+'" class="'+cssClass.download+'" download></a>' ); 88 89 var theBar = thePlayer.find( '.' + cssClass.bar ), 90 barPlayed = thePlayer.find( '.' + cssClass.barPlayed ), 91 barLoaded = thePlayer.find( '.' + cssClass.barLoaded ), 92 barTime = thePlayer.find( '.' + cssClass.barTime ), 93 timeCurrent = thePlayer.find( '.' + cssClass.timeCurrent ), 94 timeDuration = thePlayer.find( '.' + cssClass.timeDuration ), 95 volumeButton = thePlayer.find( '.' + cssClass.volumeButton ), 96 volumeAdjuster = thePlayer.find( '.' + cssClass.volumeAdjust + ' > div' ), 97 volumeDefault = 0, 98 adjustCurrentTime = function( e ) 99 { 100 theRealEvent = isTouch ? e.originalEvent.touches[ 0 ] : e; 101 theAudio.currentTime = Math.round( ( theAudio.duration * ( theRealEvent.pageX - theBar.offset().left ) ) / theBar.width() ); 102 }, 103 adjustVolume = function( e ) 104 { 105 theRealEvent = isTouch ? e.originalEvent.touches[ 0 ] : e; 106 theAudio.volume = Math.abs( ( theRealEvent.pageY - ( volumeAdjuster.offset().top + volumeAdjuster.height() ) ) / volumeAdjuster.height() ); 107 }, 108 updateLoadBar = setInterval( function() 109 { 110 //debugger 111 if(theAudio.buffered.length>0){ 112 barLoaded.width( ( theAudio.buffered.end( 0 ) / theAudio.duration ) * 100 + '%' ); 113 if( theAudio.buffered.end( 0 ) >= theAudio.duration ) 114 clearInterval( updateLoadBar ); 115 } 116 }, 100 ); 117 118 var volumeTestDefault = theAudio.volume, volumeTestValue = theAudio.volume = 0.111; 119 if( Math.round( theAudio.volume * 1000 ) / 1000 == volumeTestValue ) theAudio.volume = volumeTestDefault; 120 else thePlayer.addClass( cssClass.noVolume ); 121 122 timeDuration.html($this.attr('data-duration')); 123 timeCurrent.text( secondsToTime( 0 ) ); 124 theBar.attr('title', secondsToTime( 0 )); // добавлÑем ÑайÑл Ñо вÑеменем на Ð½Ð°Ð²Ð±Ð°Ñ 125 126 theAudio.addEventListener( 'loadeddata', function() 127 { 128 timeDuration.text( secondsToTime( theAudio.duration ) ); 129 volumeAdjuster.find( 'div' ).height( theAudio.volume * 100 + '%' ); 130 volumeDefault = theAudio.volume; 131 }); 132 133 theAudio.addEventListener( 'timeupdate', function() 134 { 135 timeCurrent.text( secondsToTime( theAudio.currentTime ) ); 136 theBar.attr('title', secondsToTime( theAudio.currentTime )); // добавлÑем ÑайÑл Ñо вÑеменем на Ð½Ð°Ð²Ð±Ð°Ñ 137 barPlayed.width( ( theAudio.currentTime / theAudio.duration ) * 100 + '%' ); 138 barTime.text(secondsToTime(theAudio.currentTime) + ' / ' + secondsToTime(theAudio.duration)); 139 }); 140 141 theAudio.addEventListener( 'volumechange', function() 142 { 143 volumeAdjuster.find( 'div' ).height( theAudio.volume * 100 + '%' ); 144 if( theAudio.volume > 0 && thePlayer.hasClass( cssClass.mute ) ) thePlayer.removeClass( cssClass.mute ); 145 if( theAudio.volume <= 0 && !thePlayer.hasClass( cssClass.mute ) ) thePlayer.addClass( cssClass.mute ); 146 }); 147 148 theAudio.addEventListener( 'ended', function() 149 { 150 thePlayer.removeClass( cssClass.playing ); 151 }); 152 153 theBar.on( eStart, function( e ) 154 { 155 adjustCurrentTime( e ); 156 theBar.on( eMove, function( e ) { adjustCurrentTime( e ); } ); 157 }) 158 .on( eCancel, function() 159 { 160 theBar.unbind( eMove ); 161 }); 162 163 volumeButton.on( 'click', function() 164 { 165 if( thePlayer.hasClass( cssClass.mute ) ) 166 { 167 thePlayer.removeClass( cssClass.mute ); 168 theAudio.volume = volumeDefault; 169 } 170 else 171 { 172 thePlayer.addClass( cssClass.mute ); 173 volumeDefault = theAudio.volume; 174 theAudio.volume = 0; 175 } 176 return false; 177 }); 178 179 volumeAdjuster.on( eStart, function( e ) 180 { 181 adjustVolume( e ); 182 volumeAdjuster.on( eMove, function( e ) { adjustVolume( e ); } ); 183 }) 184 .on( eCancel, function() 185 { 186 volumeAdjuster.unbind( eMove ); 187 }); 188 } 189 else thePlayer.addClass( cssClass.mini ); 190 191 if( isAutoPlay ) thePlayer.addClass( cssClass.playing ); 192 193 thePlayer.find( '.' + cssClass.playPause ).on( 'click', function() 194 { 195 if( thePlayer.hasClass( cssClass.playing ) ) 196 { 197 $( this ).attr( 'title', params.strPlay ).find( 'a' ).html( params.strPlay ); 198 thePlayer.removeClass( cssClass.playing ); 199 isSupport ? theAudio.pause() : theAudio.Stop(); 200 } 201 else 202 { 203 $( this ).attr( 'title', params.strPause ).find( 'a' ).html( params.strPause ); 204 thePlayer.addClass( cssClass.playing ); 205 isSupport ? theAudio.play() : theAudio.Play(); 206 } 207 return false;
208 }); 209 210 $this.replaceWith( thePlayer ); 211 }); 212 return this; 213 }; 214})( jQuery, window, document );
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.