123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246 |
- import {THEME_DEFAULT, THEME_MINI} from './constants';
- import * as lyric from './lyric';
- import * as utils from './utils';
- import * as spectrum from './spectrum';
- var root = typeof window == 'object' && window.window === window ? window :
- typeof global == 'object' && global.global === global ? global : this;
- root.mePlayer = function (options) {
- // 检查必填选项
- if (!(options.music && options.music.src)) {
- console.error('必须指定音乐地址哦~');
- return;
- }
- var musicConf = options.music,
- target = getTarget(options.target),
- theme = options.theme ? options.theme : THEME_DEFAULT,
- hasLrc = musicConf.lrc ? true : false,
- coverSrc = musicConf.cover ? musicConf.cover : 'https://unsplash.it/78/?random',
- currentThemeClass = theme === THEME_DEFAULT ? 'meplayer-container' : 'meplayer-container-mini',
- containerClass = `${currentThemeClass} ${hasLrc ? 'meplayer-haslrc' : ''} meplayer-isloading`,
- playerHTMLContent = `<div class="${containerClass}">
- <audio src=${musicConf.src}></audio>
- <div class="meplayer-info">
- <div class="meplayer-info-cover"><img src=${coverSrc} alt="cd-cover"></div>
- <div class="meplayer-meta">
- <div class="meplayer-meta-title">${musicConf.title}</div>
- <div class="meplayer-meta-author">${musicConf.author}</div>
- <div class="meplayer-meta-time-tick"><span class="meplayer-meta-time-tick-text"></span></div>
- </div>
- </div>
- <canvas class="meplayer-spectrum"></canvas>
- <div class="meplayer-lyric"><div class="meplayer-lyric-area"></div></div>
- <div class="meplayer-control"><div class="meplayer-control-play"><i class="icon-play"></i><i class="icon-pause"></i></div></div>
- <div class="meplayer-volume-bg"><div class="meplayer-volume"><i class="icon-volume"></i><div class="meplayer-volume-progress"></div></div></div>
- <div class="meplayer-duration"><i class="icon-clock"></i><span class="meplayer-duration-text">loading</span></div>
- <div class="meplayer-loadingsign"><i class="icon-spin animate-spin"></i>loading</div>
- <div class="meplayer-timeline-bg"><div class="meplayer-timeline"><div class="meplayer-timeline-passed"></div></div></div>
- </div>`;
- target.innerHTML = playerHTMLContent;
- var meplayerContainer = target.querySelector(`.${currentThemeClass}`),
- audio = target.querySelector('audio'),
- playBtn = target.querySelector('.meplayer-control-play'),
- timeTick = target.querySelector('.meplayer-meta-time-tick-text'),
- timeCount = target.querySelector('.meplayer-duration'),
- timeLine = target.querySelector('.meplayer-timeline'),
- timePassed = target.querySelector('.meplayer-timeline-passed'),
- volumeArea = target.querySelector('.meplayer-volume'),
- volumeProgress = target.querySelector('.meplayer-volume-progress'),
- lyricArea = target.querySelector('.meplayer-lyric-area'),
- canvas = target.querySelector('.meplayer-spectrum'),
- duration;
- // 设置在页面加载后立即加载音频
- audio.preload = 'auto';
- if (hasLrc) {
- lyric.parse(musicConf.lrc);
- lyric.render(lyricArea);
- } else {
- // 频谱动画初始化
- spectrum.init(canvas);
- }
- eventInit();
- // 重定义meplayer
- root.mePlayer = {
- play : play,
- pause : pause,
- toggleTheme: toggleTheme
- };
- /*
- * 工具函数
- * */
- // 给播放器绑定各种事件
- function eventInit() {
- audio.addEventListener('ended', function () {
- utils.removeClass(meplayerContainer, 'meplayer-isplaying');
- });
- audio.addEventListener('canplaythrough', function () {
- duration = this.duration;
- setTimeout(function () {
- utils.removeClass(meplayerContainer, 'meplayer-isloading');
- timeCount.querySelector('.meplayer-duration-text').innerText = utils.parseSec(duration.toFixed(0));
- }, 1000);
- });
- audio.addEventListener('durationchange', function () {
- duration = this.duration;
- });
- audio.addEventListener('timeupdate', function () {
- var curTime = (audio.currentTime).toFixed(0);
- var curTimeForLrc = (audio.currentTime).toFixed(3);
- var playPercent = 100 * (curTime / duration);
- timePassed.style.width = playPercent.toFixed(2) + '%';
- timeTick.innerText = utils.parseSec(curTime);
- if (hasLrc && theme === THEME_DEFAULT) {
- var tempLrcIndex = lyric.currentIndex(curTimeForLrc);
- var tempLrcLines = lyricArea.querySelectorAll('p');
- var tempLrcLinePre = tempLrcLines[tempLrcIndex - 1];
- var tempLrcLine = tempLrcLines[tempLrcIndex];
- var tempLrcLineNext = tempLrcLines[tempLrcIndex + 1];
- if (!tempLrcLine.className.includes('meplayer-lyric-current')) {
- utils.removeClass(lyricArea.querySelector('.meplayer-lyric-current'), 'meplayer-lyric-current');
- if (lyricArea.querySelector('.meplayer-lyric-pre')) {
- utils.removeClass(lyricArea.querySelector('.meplayer-lyric-pre'), 'meplayer-lyric-pre');
- }
- if (lyricArea.querySelector('.meplayer-lyric-next')) {
- utils.removeClass(lyricArea.querySelector('.meplayer-lyric-next'), 'meplayer-lyric-next');
- }
- utils.addClass(tempLrcLine, 'meplayer-lyric-current');
- if (tempLrcLinePre) {
- utils.addClass(tempLrcLinePre, 'meplayer-lyric-pre');
- }
- if (tempLrcLineNext) {
- utils.addClass(tempLrcLineNext, 'meplayer-lyric-next');
- }
- lyricArea.style.webkitTransform = 'translateY(-' + 20 * tempLrcIndex + 'px)';
- lyricArea.style.transform = 'translateY(-' + 20 * tempLrcIndex + 'px)';
- }
- }
- });
- var _handleMouseWheel;
- playBtn.addEventListener('click', function () {
- if (audio.paused) {
- audio.play();
- if (theme === THEME_DEFAULT && !hasLrc) {
- spectrum.draw();
- }
- // 播放状态中可以用滑轮调节音量
- meplayerContainer.addEventListener('mousewheel', function handleMouseWheel() {
- var timer = null;
- var step = 0.05;
- _handleMouseWheel = function (event) {
- if (timer) {
- clearTimeout(timer);
- }
- if (!meplayerContainer.className.includes('meplayer-adjusting-volume')) {
- utils.addClass(meplayerContainer, 'meplayer-adjusting-volume');
- }
- if (event.wheelDeltaY < 0 && audio.volume > step) {
- audio.volume -= step;
- }
- if (event.wheelDeltaY > 0 && audio.volume < 1 - step) {
- audio.volume += step;
- }
- if (theme === THEME_DEFAULT) {
- volumeProgress.style.width = audio.volume * 100 + '%';
- } else {
- volumeArea.querySelector('i').style.opacity = audio.volume;
- }
- event.preventDefault();
- timer = setTimeout(function () {
- utils.removeClass(meplayerContainer, 'meplayer-adjusting-volume');
- }, 1000);
- };
- return _handleMouseWheel;
- }());
- } else {
- audio.pause();
- spectrum.stop();
- meplayerContainer.removeEventListener('mousewheel', _handleMouseWheel);
- }
- utils.toggleClass(meplayerContainer, 'meplayer-isplaying');
- });
- timeLine.addEventListener('click', function (event) {
- var clickPercent = (event.pageX - utils.getAbsLeft(this)) / this.offsetWidth;
- timePassed.style.width = clickPercent * 100 + '%';
- audio.currentTime = (clickPercent * duration).toFixed(0);
- });
- }
- function play() {
- if (audio.paused) {
- audio.play();
- }
- }
- function pause() {
- if (!audio.paused) {
- audio.pause();
- }
- }
- function toggleTheme() {
- var step = 0.03;
- var count = 0;
- var maxCount = 200;
- utils.addClass(meplayerContainer, 'meplayer-changing-theme');
- theme = theme === THEME_DEFAULT ? THEME_MINI : THEME_DEFAULT;
- loop();
- function loop() {
- count++;
- meplayerContainer.style.opacity -= step;
- if (meplayerContainer.style.opacity <= 0) {
- step *= -1;
- meplayerContainer.style.opacity = 0;
- utils.toggleClass(meplayerContainer, 'meplayer-container-mini');
- utils.toggleClass(meplayerContainer, 'meplayer-container');
- }
- if (meplayerContainer.style.opacity < 1 && count < maxCount) {
- requestAnimationFrame(loop);
- } else {
- setTimeout(function () {
- utils.removeClass(meplayerContainer, 'meplayer-changing-theme');
- }, 500);
- }
- }
- }
- };
- if (typeof module !== 'undefined' && typeof module.exports !== 'undefined') {
- module.exports = root.mePlayer;
- }
- function getTarget(option) {
- if (typeof option === 'string') {
- return document.querySelector(option);
- } else if (option.toString().includes('HTMLDivElement')) {
- return option;
- } else {
- return document.querySelector('.meplayer');
- }
- }
|