티스토리 뷰
const musicWrap = document.querySelector(".wrap__music");
const musicImg = musicWrap.querySelector(".music__img img");
const musicSong = musicWrap.querySelector(".music__song");
const musicName = musicSong.querySelector(".name");
const musicArtist = musicSong.querySelector(".artist");
const musicProgress = musicWrap.querySelector(".music__progress");
const musicProgressBar = musicProgress.querySelector(".bar");
const musicAudio = musicProgress.querySelector("#main-audio");
const musicProgressCurrent = musicProgress.querySelector(".current");
const musicProgressDuration = musicProgress.querySelector(".duration");
const musicControl = musicWrap.querySelector(".music__control");
const musicPlay = musicControl.querySelector("#control-play");
const musicPrev = musicControl.querySelector("#control-prev");
const musicNext = musicControl.querySelector("#control-next");
const musicRepeat = musicControl.querySelector("#control-repeat");
const musicListBtn = musicControl.querySelector("#control-list");
const musicList = musicWrap.querySelector(".music__list");
const musicListClose = musicList.querySelector(".close");
const musicListUl = musicList.querySelector(".list ul");
let musicIndex = Math.floor((Math.random() * allMusic.length) + 1 );
// 음악정보 뿌러주기
function loadMusic(num){
musicImg.src = `images/${allMusic[num - 1].img}.jpg`;
musicImg.alt = allMusic[num - 1].name;
musicName.innerText = allMusic[num - 1].name;
musicArtist.innerText = allMusic[num - 1].artist;
musicAudio.src = `songs/${allMusic[num - 1].audio}.mp3`;
}
// 음악재생
function playMusic(){
musicWrap.classList.add("paused");
musicPlay.innerText = "pause";
musicPlay.setAttribute("title", "재생")
musicAudio.play();
}
// 음악정지
function pauseMusic(){
musicWrap.classList.remove("paused");
musicPlay.innerText = "play_arrow";
musicPlay.setAttribute("title", "정지")
musicAudio.pause();
}
// 이전음악
function prevMusic(){
musicIndex == 1 ? musicIndex = allMusic.length : musicIndex--;
loadMusic(musicIndex);
playMusic();
}
// 다음음악
function nextMusic(){
musicIndex == allMusic.length ? musicIndex = 1 : musicIndex++;
loadMusic(musicIndex);
playMusic();
}
// 뮤직 진행바
musicAudio.addEventListener("timeupdate", (e) => {
//console.log(e)
const currentTime = e.target.currentTime;
const duration = e.target.duration;
let progressWidth = (currentTime/duration)*100;
musicProgressBar.style.width = `${progressWidth}%`;
//전체 시간
musicAudio.addEventListener("loadeddata", () => {
let audioDuration = musicAudio.duration;
let totalMin = Math.floor(audioDuration / 60);
let totalSec = Math.floor(audioDuration % 60);
if(totalSec < 10) totalSec = `0${totalSec}`;
musicProgressDuration.innerText = `${totalMin}:${totalSec}`;
});
//현재 시간
let currentMin = Math.floor(currentTime / 60);
let currentSec = Math.floor(currentTime % 60);
if(currentSec < 10) currentSec = `0${currentSec}`;
musicProgressCurrent.innerText = `${currentMin}:${currentSec}`;
});
// 재생/정지 버튼
musicPlay.addEventListener("click", () => {
const isMusicPaused = musicWrap.classList.contains("paused")
isMusicPaused ? pauseMusic() : playMusic();
})
// 이전 버튼
musicPrev.addEventListener("click", () => {
prevMusic();
playListMusic();
});
// 다음 버튼
musicNext.addEventListener("click", () => {
nextMusic();
playListMusic();
});
// 진행 버튼
musicProgress.addEventListener("click", (e) => {
let progressWidth = musicProgress.clientWidth;
let clickedOffsetX = e.offsetX;
let songDuration = musicAudio.duration
musicAudio.currentTime = (clickedOffsetX / progressWidth) * songDuration;
playMusic();
playListMusic();
})
// 반복 버튼
musicRepeat.addEventListener("click", (e) => {
let getText = musicRepeat.innerText;
switch(getText){
case "repeat":
musicRepeat.innerText = "repeat_one";
musicRepeat.setAttribute("title", "한곡 반복")
break;
case "repeat_one":
musicRepeat.innerText = "shuffle";
musicRepeat.setAttribute("title", "랜덤 반복")
break;
case "shuffle":
musicRepeat.innerText = "repeat";
musicRepeat.setAttribute("title", "전체 반복")
break;
};
});
// 오디오가 끝나고
musicAudio.addEventListener("ended", () => {
let getText = musicRepeat.innerText;
switch(getText){
case "repeat":
nextMusic();
break;
case "repeat_one":
loadMusic(musicIndex);
playMusic();
playListMusic();
break;
case "shuffle":
let randIndex = Math.floor((Math.random() * allMusic.length) + 1);
do {
randIndex = Math.floor((Math.random() * allMusic.length) + 1);
} while (musicIndex == randIndex);
// musicIndex = randIndex;
loadMusic(randIndex);
playMusic();
playListMusic();
break;
}
})
// 뮤직 리스트 버튼
musicListBtn.addEventListener("click", () => {
musicList.classList.add("show");
})
// 뮤직 리스트 닫기 버튼
musicListClose.addEventListener("click", () => {
musicList.classList.remove("show");
})
// 뮤직 리스트 구현하기
for(let i=0; i<allMusic.length; i++){
let li = `
<li data-index="${i + 1}">
<div>
<em>${allMusic[i].name}</em>
<p>${allMusic[i].artist}</p>
</div>
<audio class="${allMusic[i].audio}" src="songs/${allMusic[i].audio}.mp3"></audio>
<span id="${allMusic[i].audio}" class="audio-duration">3:36</span>
</li>
`;
musicListUl.insertAdjacentHTML("beforeend", li);
let liAudioDuration = musicListUl.querySelector(`#${allMusic[i].audio}`);
let liAudio = musicListUl.querySelector(`.${allMusic[i].audio}`);
liAudio.addEventListener("loadeddata", () => {
let audioDuration = liAudio.duration;
let totalMin = Math.floor(audioDuration / 60);
let totalSec = Math.floor(audioDuration % 60);
if(totalSec < 10) totalSec = `0${totalSec}`;
liAudioDuration.innerText = `${totalMin}:${totalSec}`;
liAudioDuration.setAttribute("data-duration", `${totalMin}:${totalSec}`);
})
}
// 뮤직 리스트 버튼
function playListMusic(){
const musicListAll = musicListUl.querySelectorAll("li");
for(let j=0; j<musicListAll.length; j++){
let audioTag = musicListAll[j].querySelector(".audio-duration");
if(musicListAll[j].classList.contains("playing")){
musicListAll[j].classList.remove("playing");
let adDuration = audioTag.getAttribute("data-duration");
audioTag.innerText = adDuration;
}
if(musicListAll[j].getAttribute("data-index") == musicIndex){
musicListAll[j].classList.add("playing");
audioTag.innerText = "재생중";
}
musicListAll[j].setAttribute("onclick", "clicked(this)")
}
}
// 뮤직 리스트의 곡 클릭하기
function clicked(el){
let getLiIndex = el.getAttribute("data-index");
musicIndex = getLiIndex;
loadMusic(musicIndex);
musicList.classList.remove("show");
playMusic();
playListMusic();
}
// 페이지 로딩 후 실행
window.addEventListener("load", () => {
loadMusic(musicIndex);
playListMusic();
})
* {
margin: 0;
padding: 0;
box-sizing: border-box;
font-family: Poppins;
}
:root {
--pink : #FF74A4;
--violet : #9F6EA3;
--white : #fff;
--lightshadow : rgba(0, 0, 0, 0.15);
--lightblack : #515C6F;
--pinkshadow : #FFCBDD;
--darkwhite : #CECACA;
}
body {
height: 100vh;
background: linear-gradient(var(--pink) 0%, var(--violet) 100%);
}
.wrap__music {
display: flex;
align-items: center;
justify-content: center;
min-height: 100%;
user-select: none;
}
.music__inner {
width: 380px;
padding: 25px 30px;
overflow: hidden;
position: relative;
border-radius: 15px;
background: var(--white);
box-shadow: 0px 6px 15px var(--lightshadow);
}
.music__top {
display: flex;
align-items: center;
justify-content: space-between;
}
.music__top i {
font-size: 30px;
color: var(--lightblack);
}
.music__top h3 {
font-size: 18px;
color: var(--lightblack);
font-weight: 500;
}
.music__img {
width: 100%;
height: 256px;
overflow: hidden;
border-radius: 15px;
margin-top: 25px;
box-shadow: 0px 6px 12px var(--lightshadow);
}
.music__img img {
width: 100%;
height: 100%;
vertical-align: top;
object-fit: cover;
}
.music__song {
text-align: center;
margin: 30px;
}
.music__song p {
color: var(--lightblack);
}
.music__song p.name {
font-size: 21px;
}
.music__song p.artist {
font-size: 18px;
opacity: 0.9;
line-height: 35px;
font-weight: 300;
}
.music__progress {
height: 6px;
width: 100%;
border-radius: 10px;
background: #f0f0f0;
cursor: pointer;
}
.music__progress .bar {
height: inherit;
width: 0%;
position: relative;
border-radius: inherit;
background: linear-gradient(90deg, var(--pink) 0%, var(--violet) 100%);
}
.music__progress .timer {
margin-top: 2px;
display: flex;
align-items: center;
justify-content: space-between;
color: var(--lightblack);
font-size: 0.9em;
pointer-events: none;
}
.music__control {
display: flex;
align-items: center;
justify-content: space-between;
margin-top: 40px;
}
.music__control i {
font-size: 28px;
user-select: none;
background: linear-gradient(90deg, var(--pink) 0%, var(--violet) 100%);
background-clip: text;
-webkit-background-clip: text;
-webkit-text-fill-color: transparent;
}
.music__control i:nth-child(2),
.music__control i:nth-child(4) {
font-size: 40px;
}
.music__control .play-pause {
width: 54px; height: 54px;
display: flex;
align-items: center;
justify-content: center;
border-radius: 50%;
background: linear-gradient(var(--white) 0%, var(--darkwhite) 100%);
box-shadow: 0px 0px 0px 2px var(--pink);
z-index: 1;
}
.music__control .play-pause::before {
content: '';
width: 40px; height: 40px;
border-radius: inherit;
background: linear-gradient(var(--pink) 0%, var(--violet) 100%);
position: absolute;
z-index: -1;
}
.music__control .play-pause i {
-webkit-text-fill-color: var(--white);
opacity: 0.8;
}
.music__list {
position: absolute;
background: var(--white);
width: 100%;
left: 0;
z-index: 10;
border-radius: 10px;
padding: 15px 30px;
box-shadow: 0 -5px 10px rgba(0,0,0,0.1);
transition: all 0.15s ease-out;
bottom: -400px;
opacity: 0;
pointer-events: none;
}
.music__list.show {
bottom: 0px;
opacity: 1;
pointer-events: auto;
}
.music__list .title {
display: flex;
align-items: center;
justify-content: space-between;
color: var(--lightblack);
margin-bottom: 10px;
}
.music__list .title .queue {
vertical-align: -5px;
}
.music__list .list {
color: var(--lightblack);
}
.music__list .list > ul {
max-height: 260px;
margin: 10px 0;
overflow: auto;
}
.music__list .list > ul::-webkit-scrollbar {
width: 0;
}
.music__list .list > ul > li {
display: flex;
align-items: center;
justify-content: space-between;
border-bottom: 1px solid #e5e5e5;
padding-bottom: 5px;
margin-bottom: 5px;
}
.music__list .list > ul > li.playing {
color: var(--pink);
}
.music__list .list > ul > li > div em {
font-style: normal;
}
.music__list .list > ul > li > div p {
opacity: 0.8;
}
'Javascript > 연습, 실습' 카테고리의 다른 글
타자 연습 (0) | 2022.04.14 |
---|---|
카드 뒤집기 (0) | 2022.04.14 |
js로 css 제어하기 (0) | 2022.02.11 |
puzzle 만들기 (0) | 2022.01.29 |
댓글
© 2018 webstoryboy