├── README.md ├── css └── style.css ├── js ├── script.js ├── doubleLinkedList.js └── utils.js └── index.html /README.md: -------------------------------------------------------------------------------- 1 | # Music_Player_Using_LinkedList -------------------------------------------------------------------------------- /css/style.css: -------------------------------------------------------------------------------- 1 | * { 2 | margin: 0; 3 | padding: 0; 4 | box-sizing: border-box; 5 | } 6 | 7 | /* *** global classes ****** */ 8 | 9 | .flex { 10 | display: flex; 11 | align-items: center; 12 | justify-content: center; 13 | } 14 | 15 | .down-margin { 16 | margin-bottom: 25px; 17 | } 18 | 19 | .right-margin { 20 | margin-right: 15px; 21 | } 22 | 23 | .icon-color { 24 | color: white; 25 | } 26 | 27 | /* *** global classes end */ 28 | 29 | .outer-wrapper { 30 | width: 100%; 31 | height: 100vh; 32 | background-color: #243441; 33 | flex-wrap: wrap; 34 | } 35 | 36 | .music-player-wrapper { 37 | margin: 10px; 38 | height: 400px; 39 | width: 400px; 40 | border: 3px solid #21282c; 41 | box-shadow: 5px 10px 5px rgba(0, 0, 0, 0.3); 42 | border-radius: 10px; 43 | flex-direction: column; 44 | } 45 | 46 | /* styling for music information */ 47 | 48 | .music-info-wrapper { 49 | flex: 1; 50 | width: 100%; 51 | } 52 | 53 | .music-info { 54 | color: white; 55 | font-size: 30px; 56 | font-weight: 600; 57 | } 58 | 59 | /* styling for music icons */ 60 | 61 | .music-icons-wrapper { 62 | width: 100%; 63 | } 64 | 65 | /* next pre play pause styling */ 66 | .music-icons { 67 | justify-content: space-around; 68 | } 69 | 70 | .play-pause-btn-wrapper i { 71 | color: white; 72 | cursor: pointer; 73 | } 74 | 75 | /* previous and next btn */ 76 | .previous-btn-wrapper { 77 | cursor: pointer; 78 | } 79 | 80 | .next-btn-wrapper { 81 | cursor: pointer; 82 | } 83 | -------------------------------------------------------------------------------- /js/script.js: -------------------------------------------------------------------------------- 1 | // Variables 2 | const musicTitle = document.querySelector(".music-info"); 3 | 4 | // playpause previous next 5 | const prevBtn = document.querySelector(".previous-btn-wrapper"); 6 | const nextBtn = document.querySelector(".next-btn-wrapper"); 7 | const playPauseBtn = document.querySelector(".play-pause-btn-wrapper"); 8 | 9 | // timer config 10 | let currentTime = document.querySelector(".current-time"); 11 | let musicSlider = document.querySelector(".music-slider"); 12 | let endTime = document.querySelector(".total-duration"); 13 | 14 | // volume 15 | let volumeSlider = document.querySelector(".volume-slider"); 16 | 17 | // flag for play pause 18 | let isPlaying = false; 19 | 20 | // create new music object and set default music 21 | let musicObj = document.createElement("audio"); 22 | musicObj.src = 23 | "https://files.freemusicarchive.org/storage-freemusicarchive-org/music/WFMU/Broke_For_Free/Directionless_EP/Broke_For_Free_-_01_-_Night_Owl.mp3"; 24 | 25 | // Update music slider 26 | setInterval(updateMusicSlider, 500); 27 | 28 | // update color for prev and next btn 29 | changePrevNextColor(); 30 | 31 | /* ** Event Listner for various events ** */ 32 | 33 | // event listner for play pause 34 | playPauseBtn.addEventListener("click", () => { 35 | // console.log(musicObj.duration); 36 | playpauseTrack(); 37 | }); 38 | 39 | // event listner for next music button 40 | nextBtn.addEventListener("click", () => { 41 | isPlaying = false; 42 | const resultObj = dll.traverse(1); 43 | 44 | if (resultObj != 0) { 45 | musicObj.src = resultObj.path; 46 | playpauseTrack(); 47 | } 48 | changeMusicTitle(resultObj.name); 49 | changePrevNextColor(); 50 | }); 51 | 52 | // event listner for previous button 53 | prevBtn.addEventListener("click", () => { 54 | isPlaying = false; 55 | const resultObj = dll.traverse(-1); 56 | 57 | if (resultObj != 0) { 58 | musicObj.src = resultObj.path; 59 | playpauseTrack(); 60 | } 61 | changeMusicTitle(resultObj.name); 62 | changePrevNextColor(); 63 | }); 64 | 65 | // event listner for changing volume of music 66 | volumeSlider.addEventListener("change", () => { 67 | musicObj.volume = volumeSlider.value / 100; 68 | }); 69 | 70 | // event listner for changing position of music 71 | musicSlider.addEventListener("change", () => { 72 | changeMusicPos(); 73 | }); 74 | -------------------------------------------------------------------------------- /js/doubleLinkedList.js: -------------------------------------------------------------------------------- 1 | // Creating a node 2 | class Node { 3 | constructor(name, length, path) { 4 | this.musicNode = { 5 | name: name, 6 | length: length, 7 | path: path, 8 | }; 9 | this.prev = null; 10 | this.next = null; 11 | } 12 | } 13 | 14 | // creating double liked list obj and pointer 15 | class DoubllyLinkedList { 16 | constructor() { 17 | this.head = null; 18 | this.tail = null; 19 | this.length = 0; 20 | this.tempPos = null; 21 | } 22 | 23 | // push node to DLL 24 | push(name, length, path) { 25 | const newNode = new Node(name, length, path); 26 | if (this.length === 0) { 27 | this.head = newNode; 28 | this.tail = newNode; 29 | } else { 30 | this.tail.next = newNode; 31 | newNode.prev = this.tail; 32 | this.tail = newNode; 33 | } 34 | this.length++; 35 | } 36 | 37 | // set position of current node 38 | // default is pointer of head node 39 | setDefaulltPointer() { 40 | this.tempPos = this.head; 41 | } 42 | 43 | // traverse DLL and return music obj 44 | traverse(direction) { 45 | // forward direction 46 | if (direction === 1 && this.tempPos.next != null) { 47 | this.tempPos = this.tempPos.next; 48 | return this.tempPos.musicNode; 49 | } else if (direction === -1 && this.tempPos.prev != null) { 50 | //backward direction 51 | this.tempPos = this.tempPos.prev; 52 | return this.tempPos.musicNode; 53 | } else { 54 | return 0; 55 | } 56 | } 57 | 58 | // check for position of node 59 | nodePosition() { 60 | if (this.tempPos.next == null) { 61 | return -1; // last pos 62 | } else if (this.tempPos.prev == null) { 63 | return 1; // first pos 64 | } else { 65 | return 0; // middle pos 66 | } 67 | } 68 | } 69 | 70 | // inserting music in double linked list 71 | const dll = new DoubllyLinkedList(); 72 | dll.push( 73 | "Shipping Lanes", 74 | 1, 75 | "https://files.freemusicarchive.org/storage-freemusicarchive-org/music/WFMU/Broke_For_Free/Directionless_EP/Broke_For_Free_-_01_-_Night_Owl.mp3" 76 | ); 77 | dll.push( 78 | "Enthusiast", 79 | 2, 80 | "https://files.freemusicarchive.org/storage-freemusicarchive-org/music/no_curator/Tours/Enthusiast/Tours_-_01_-_Enthusiast.mp3" 81 | ); 82 | dll.push( 83 | "Night Owl", 84 | 3, 85 | "https://files.freemusicarchive.org/storage-freemusicarchive-org/music/ccCommunity/Chad_Crouch/Arps/Chad_Crouch_-_Shipping_Lanes.mp3" 86 | ); 87 | 88 | dll.setDefaulltPointer(); 89 | -------------------------------------------------------------------------------- /js/utils.js: -------------------------------------------------------------------------------- 1 | function playpauseTrack() { 2 | if (!isPlaying) playTrack(); 3 | else pauseTrack(); 4 | } 5 | 6 | // play music function 7 | function playTrack() { 8 | musicObj.play(); 9 | isPlaying = true; 10 | playPauseBtn.innerHTML = ''; 11 | } 12 | 13 | // pause music function 14 | function pauseTrack() { 15 | musicObj.pause(); 16 | isPlaying = false; 17 | playPauseBtn.innerHTML = ''; 18 | } 19 | 20 | // change title 21 | function changeMusicTitle(name) { 22 | if (name != undefined) { 23 | musicTitle.innerHTML = name; 24 | } 25 | } 26 | 27 | // reset music timer 28 | function resetMusicTimer() { 29 | currentTime.innerHTML = "00:00"; 30 | endTime.innerHTML = "00:00"; 31 | musicSlider.value = 0; 32 | } 33 | 34 | // update music slider 35 | function updateMusicSlider() { 36 | let musicPos = 0; 37 | if (musicObj.duration != musicObj.currentTime) { 38 | let instantTime = Math.ceil(musicObj.currentTime); 39 | let duration = Math.ceil(musicObj.duration); 40 | let durationMin = Math.floor(duration / 60); 41 | let durationSec = Math.floor(duration % 60); 42 | 43 | let currentMin = Math.floor(instantTime / 60); 44 | let currentSec = Math.floor(instantTime % 60); 45 | 46 | musicPos = (instantTime * 100) / duration; 47 | 48 | musicSlider.value = musicPos; 49 | 50 | // for palying time 51 | if (currentSec < 10) { 52 | currentTime.innerHTML = `0${currentMin}:0${currentSec}`; 53 | } else { 54 | currentTime.innerHTML = `0${currentMin}:${currentSec}`; 55 | } 56 | 57 | // for duration 58 | if (durationSec != NaN) { 59 | if (durationSec < 10) { 60 | endTime.innerHTML = `0${durationMin}:0${durationSec}`; 61 | } else { 62 | endTime.innerHTML = `0${durationMin}:${durationSec}`; 63 | } 64 | } 65 | } else { 66 | resetMusicTimer(); 67 | pauseTrack(); 68 | } 69 | } 70 | 71 | // for changing music position 72 | function changeMusicPos() { 73 | let changedSliderPos = musicSlider.value; 74 | let changedMusicPos = (changedSliderPos * musicObj.duration) / 100; 75 | musicObj.currentTime = changedMusicPos; 76 | } 77 | 78 | // change prev next btn color 79 | function changePrevNextColor() { 80 | let position = dll.nodePosition(); 81 | 82 | if (position === 1) { 83 | prevBtn.style.color = "black"; 84 | nextBtn.style.color = "white"; 85 | } else if (position === -1) { 86 | prevBtn.style.color = "white"; 87 | nextBtn.style.color = "black"; 88 | } else { 89 | prevBtn.style.color = "white"; 90 | nextBtn.style.color = "white"; 91 | } 92 | } 93 | -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | Music Player 8 | 9 | 13 | 14 | 15 | 16 | 17 |
18 | 19 |
20 | 21 |
22 |
Shipping Lanes
23 |
24 | 25 |
26 |
27 | 28 |
29 | 30 |
31 | 32 |
33 | 34 |
35 | 36 |
37 | 38 |
39 |
40 | 41 |
42 | 43 |
44 |
00:00
45 |
46 | 47 |
48 | 55 |
56 | 57 |
58 |
00:00
59 |
60 |
61 | 62 |
63 | 64 |
65 | 66 |
67 | 68 |
69 | 76 |
77 | 78 |
79 | 80 |
81 |
82 |
83 |
84 |
85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | --------------------------------------------------------------------------------