1

I am creating a music player that is both without a playlist and with a playlist. the music starts playing when either the play button is clicked or one of the tracks in the playlist is clicked on. And only one track must be played at the time.

here is my code : DEMO

$.fn.MusicPlayer = function(options) {
  var settings = $.extend({
    // These are the defaults
    title: "",
    track_URL: "",
    load_playlist: ""
  }, options);
  var audio, thisObj, playPauseBTN;
  audio = new Audio();
  thisObj = this;
  playPauseBTN = $(".playButton", thisObj);

  //Statuses Evnts
  $(audio).on("playing", function() {
    togglePlying(playPauseBTN, true);
    $(playPauseBTN).addClass("pause");
  });
  $(audio).on("pause", function() {
    togglePlying(playPauseBTN, false);
    $(playPauseBTN).removeClass("pause");
  });


  thisObj.each(function() {
    audio.src = settings.track_URL;
    $(".title", thisObj).text(settings.title);

    if (settings.load_playlist == "true") {
      $(thisObj).css("height", "140px");
      $(thisObj).append("<div class='playlist'></div>");
      $(".playlist", thisObj).append("<div class='row' data-src='https://p.scdn.co/mp3-preview/c92cc644b1eb5094ce65cf561c41b0c6d9f3faaa'>music 1</div>");
      $(".playlist", thisObj).append("<div class='row' data-src='https://p.scdn.co/mp3-preview/dc73c2b8aa08c7b5ac2c72813326fbd6aa65787b'>music 2</div>");
      $(".playlist", thisObj).append("<div class='row' data-src='https://p.scdn.co/mp3-preview/b2da3e7ee2834c24fbf5a0927e59d34cc618e30e'>music 3</div>");
    }
  });


  $(playPauseBTN, thisObj).on("click tap", function() {
    manageAudio();
  });

  $(".playlist > .row", thisObj).on("click tap", function() {
    audio.src = $(this).attr("data-src");
    manageAudio();
  });


  function manageAudio() {
    if (audio.paused) {
      audio.play();
      $('.playButton.playing').click();

      $(thisObj).addClass("bekhon");
      $(".sMusicPlyaer").removeClass("nakhon ");
    } else {
      audio.pause();

      $(thisObj).addClass("nakhon");
      $(".sMusicPlyaer").removeClass("bekhon");
    }
  }
}


// Utility functions
function togglePlying(aClassName, bool) {
  $(aClassName).toggleClass("playing", bool);
}

$("#player1").MusicPlayer({
  title: "title 1",
  track_URL: "https://rjmediamusic.com/media/mp3/mp3-256/Alireza-JJ-Sijal-Nassim-Ki-Khoobe-Ki-Bad-(Ft-Behzad-Leito-Sami-Low-AFX).mp3"
});

$("#player2").MusicPlayer({
  title: "title 2",
  track_URL: "http://myst729.qiniudn.com/within-temptation_pale.mp3",
  load_playlist: "true"
});

$("#player3").MusicPlayer({
  title: "title 3",
  track_URL: "https://p.scdn.co/mp3-preview/657f7141682f667253bf9c3afab5feebccf75105"
});
body {
  background: url(http://wallpapercave.com/wp/VkyGWEi.jpg) no-repeat;
  background-size: cover;
}

.sMP {
  background: rgba(255, 255, 255, 0.5);
  color: #000;
  width: 400px;
  height: 50px;
  margin: 10px;
}

.playButton {
  background: url(https://cdn4.iconfinder.com/data/icons/standard-free-icons/139/Play01-64.png);
  background-size: 30px 30px !important;
  width: 30px;
  height: 30px;
}

.playButton.pause {
  background: url(https://cdn4.iconfinder.com/data/icons/ionicons/512/icon-pause-48.png);
}

.row {
  border: 1px solid black;
  margin: 5px 0 5px 0;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="sMP" id="player1">
  <div class="playButton"></div>
  <div class="title"></div>
</div>
<div class="sMP" id="player2">
  <div class="playButton"></div>
  <div class="title"></div>
</div>
<div class="sMP" id="player3">
  <div class="playButton"></div>
  <div class="title"></div>
</div>

The above code does a part of the code. It plays one track at the time, but if a track from the same playlist is clicked then it pauses the track. (which must start playing it instead). To test it, click on music 1 from the playlist, and while it is playing, click on music 2. You will see that the track pauses instead of start playing.

Any idea to fix that ?

Community
  • 1
  • 1
DannyBoy
  • 434
  • 5
  • 21

1 Answers1

2

Play the audio after a timeout:

function manageAudio() {
    if (audio.paused) {

 //play after 150ms
    setTimeout(function () {      
       audio.play();
    }, 150);

      $('.playButton.playing').click();

      $(thisObj).addClass("bekhon");
      $(".sMusicPlyaer").removeClass("nakhon ");
    } else {
      audio.pause();

      $(thisObj).addClass("nakhon");
      $(".sMusicPlyaer").removeClass("bekhon");
    }
  }

check out: How to prevent "The play() request was interrupted by a call to pause()" error?

Community
  • 1
  • 1
dardan.g
  • 689
  • 7
  • 17
  • Thank you for your respond. Indeed it works, how ever there is an error in console that is `jquery.min.js:2 Uncaught RangeError: Maximum call stack size exceeded(…)`. Based on [this](http://stackoverflow.com/a/6095695/6797135), there there is a loop between functions that I think its play() and pause(). Do you suggest any way to fix that ? Thanks [**UPDATED DEMO**](https://jsfiddle.net/danials/yqnc9n8b/1/) – DannyBoy Oct 31 '16 at 02:06
  • 1
    check ` $(audio).on("playing", function() { togglePlying(playPauseBTN, true); $(playPauseBTN).addClass("pause"); });` it seems that it calls playPauseBTN event multiple times because the second parameter is set to true (put a console.log on manageAudio() method). – dardan.g Oct 31 '16 at 08:50