MPlayer(初稿)
<style>#mplayer {
--path: polygon(5% 0, 5% 100%, 100% 50%);
--prg: 0%;
margin-inline: auto;
margin-top: 100px;
width: 300px;
height: 160px;
border-radius: 5px;
background: linear-gradient(to right bottom, olive,teal);
box-shadow: 0 0 4px 0 gray;
color: cyan;
position: relative;
display: grid;
place-items: center;
}
#mplayer::before, #mplayer::after {
position: absolute;
top: 0px;
}
#mplayer::before {}
#mplayer::after {
content: 'Mplayer';
width: 100%;
height: 40px;
line-height: 40px;
border-radius: 5px 5px 0 0;
background: radial-gradient(5px circle at 15px, snow, snow 4px, transparent 5px) no-repeat;
padding-left: 25px;
box-sizing: border-box;
}
#mbtn, #mprog, #mMsg {
position: absolute;
cursor: pointer;
}
#mbtn {
left: 10px;
bottom: 10px;
width: 30px;
height: 30px;
border-radius: 50%;
border: 2px solid cyan;
cursor: pointer;
display: grid;
place-items: center;
}
#mbtn:after {
position: absolute;
content: '';
width: 50%;
height: 50%;
background: cyan;
clip-path: var(--path);
}
#mprog {
width: calc(100% - 155px);
height: 30px;
right: 100px;
bottom: 10px;
background: linear-gradient(to right, cyan var(--prg), silver var(--prg), silver 0) no-repeat 0 50% / 100% 2px;
}
#mMsg {
right: 10px;
bottom: 5px;
height: 40px;
line-height: 40px;
font-size: 14px;
}
.pp {
position: absolute;
width: 1px;
min-height: 2px;
transform-origin: 0 50%;
transition: height .16s linear;
display: grid;
place-items: start center;
}
</style>
<audio id="aud" src="https://music.163.com/song/media/outer/url?id=2070182112" autoplay loop></audio>
<div id="mplayer">
<span id="mbtn"></span>
<span id="mprog"></span>
<span id="mMsg">00:00/00:00</span>
</div>
<script>
const tt = Math.floor(mplayer.clientWidth / 4 - 5);
let pps = [];
Array(tt).fill('').forEach((_,k) => {
let sp = document.createElement('span');
sp.className = 'pp';
sp.style.cssText += `
left: ${10 + 4 * k}px;
background: linear-gradient(to bottom, snow, cyan, snow);
`;
pps.push(sp);
mplayer.prepend(sp);
});
(function update() {
let output = [...new Array(tt).keys()].map((v,k) => Math.floor(Math.random() * (aud.paused ? 0 : 80 - Math.random() * 160)));
for(let j = 0; j < tt ; j++) {
pps.style.height = output + 'px';
}
window.requestAnimationFrame(update);
})();
mbtn.onclick = () => aud.paused ? aud.play() : aud.pause();
mprog.onclick = (e) => aud.currentTime = aud.duration * e.offsetX / mprog.offsetWidth;
mprog.onmousemove = (e) => mprog.title = s2m(aud.duration * e.offsetX / mprog.offsetWidth);
aud.onplaying = aud.onpause = () => mState();
aud.ontimeupdate = () => {
mplayer.style.setProperty('--prg', aud.currentTime / aud.duration * 100 + '%');
mMsg.innerText = s2m(aud.currentTime) + '/' + s2m(aud.duration);
};
const mState = () => {
const path1 = 'polygon(5% 0, 5% 100%, 100% 50%)';
const path2 = 'polygon(40% 0, 0 0, 0 100%, 40% 100%, 40% 0, 60% 0, 60% 100%, 100% 100%, 100% 0)';
if(aud.paused) {
mplayer.style.setProperty('--path', path1);
}else{
mplayer.style.setProperty('--path', path2);
}
};
const s2m = (seconds) => {
if (!seconds) return '00:00';
let min = parseInt(seconds / 60), sec = parseFloat(Math.floor(seconds) % 60);
if(min < 10) min = '0' + min;
if(sec < 10) sec = '0' + sec;
return min + ':' + sec;
};
</script>
<h2>代码欢迎修改、使用、传播</h2>
<div id="hEdiv"><pre id="hEpre">
<style>
#mplayer {
--path: polygon(5% 0, 5% 100%, 100% 50%);
--prg: 0%;
margin-inline: auto;
margin-top: 100px;
width: 300px;
height: 160px;
border-radius: 5px;
background: linear-gradient(to right bottom, olive,teal);
box-shadow: 0 0 4px 0 gray;
color: cyan;
position: relative;
display: grid;
place-items: center;
}
#mplayer::before, #mplayer::after {
position: absolute;
top: 0px;
}
#mplayer::before {}
#mplayer::after {
content: 'Mplayer';
width: 100%;
height: 40px;
line-height: 40px;
border-radius: 5px 5px 0 0;
background: radial-gradient(5px circle at 15px, snow, snow 4px, transparent 5px) no-repeat;
padding-left: 25px;
box-sizing: border-box;
}
#mbtn, #mprog, #mMsg {
position: absolute;
cursor: pointer;
}
#mbtn {
left: 10px;
bottom: 10px;
width: 30px;
height: 30px;
border-radius: 50%;
border: 2px solid cyan;
cursor: pointer;
display: grid;
place-items: center;
}
#mbtn:after {
position: absolute;
content: '';
width: 50%;
height: 50%;
background: cyan;
clip-path: var(--path);
}
#mprog {
width: calc(100% - 155px);
height: 30px;
right: 100px;
bottom: 10px;
background: linear-gradient(to right, cyan var(--prg), silver var(--prg), silver 0) no-repeat 0 50% / 100% 2px;
}
#mMsg {
right: 10px;
bottom: 5px;
height: 40px;
line-height: 40px;
font-size: 14px;
}
.pp {
position: absolute;
width: 1px;
min-height: 2px;
transform-origin: 0 50%;
transition: height .16s linear;
display: grid;
place-items: start center;
}
</style>
<audio id="aud" src="https://music.163.com/song/media/outer/url?id=2070182112" autoplay loop></audio>
<div id="mplayer">
<span id="mbtn"></span>
<span id="mprog"></span>
<span id="mMsg">00:00/00:00</span>
</div>
<script>
const tt = Math.floor(mplayer.clientWidth / 4 - 5);
let pps = [];
Array(tt).fill('').forEach((_,k) => {
let sp = document.createElement('span');
sp.className = 'pp';
sp.style.cssText += `
left: ${10 + 4 * k}px;
background: linear-gradient(to bottom, snow, cyan, snow);
`;
pps.push(sp);
mplayer.prepend(sp);
});
(function update() {
let output = [...new Array(tt).keys()].map((v,k) => Math.floor(Math.random() * (aud.paused ? 0 : 80 - Math.random() * 160)));
for(let j = 0; j < tt ; j++) {
pps.style.height = output + 'px';
}
window.requestAnimationFrame(update);
})();
mbtn.onclick = () => aud.paused ? aud.play() : aud.pause();
mprog.onclick = (e) => aud.currentTime = aud.duration * e.offsetX / mprog.offsetWidth;
mprog.onmousemove = (e) => mprog.title = s2m(aud.duration * e.offsetX / mprog.offsetWidth);
aud.onplaying = aud.onpause = () => mState();
aud.ontimeupdate = () => {
mplayer.style.setProperty('--prg', aud.currentTime / aud.duration * 100 + '%');
mMsg.innerText = s2m(aud.currentTime) + '/' + s2m(aud.duration);
};
const mState = () => {
const path1 = 'polygon(5% 0, 5% 100%, 100% 50%)';
const path2 = 'polygon(40% 0, 0 0, 0 100%, 40% 100%, 40% 0, 60% 0, 60% 100%, 100% 100%, 100% 0)';
if(aud.paused) {
mplayer.style.setProperty('--path', path1);
}else{
mplayer.style.setProperty('--path', path2);
}
};
const s2m = (seconds) => {
if (!seconds) return '00:00';
let min = parseInt(seconds / 60), sec = parseFloat(Math.floor(seconds) % 60);
if(min < 10) min = '0' + min;
if(sec < 10) sec = '0' + sec;
return min + ':' + sec;
};
</script>
</pre></div>
<script type="module">
import hlight from 'https://638183.freep.cn/638183/web/mod/helight.js';
hlight.hl(hEdiv, hEpre);
</script> 这个带进度条和小频谱的播放器{:4_187:} 非常清晰的每一步设置。感觉按钮的小三角有点靠左了点,当然从数值设置上没问题呢,可能是误觉。
看两个竖线的暂停取的0 0,小三角已经取5%了,还是觉得左,肯定是视觉问题。不管这个了{:4_173:} 这个好,可以跟着学习每一种样式的css设置,还能学习在js里是如何控制的{:4_199:} 有漂亮的小播,还有进度条和频谱,还有名字展示。很完美{:4_187:} 好像评分后需要刷新才能自动播放,记得以前把js里的内容包裹起来就不受影响了? 这个小播长得可俊了。。
背景渐变色彩变化有点立体的感觉。。。
按纽进度条时间显示十分全面。。
还有频谱跳跃更显灵动。。
看着就喜欢。{:4_173:} 老师还给了源码,里面显示之前单独封起来的CSS和JS文件。。
这个对小白来说太棒了,很是友好。。{:4_173:}
记得有一版是背景透明的小播,这个背景也可以变透明的吧。。
或者换个漂亮的山水背景。。{:4_173:} 花飞飞 发表于 2024-12-8 17:32
记得有一版是背景透明的小播,这个背景也可以变透明的吧。。
或者换个漂亮的山水背景。。
前面那个是复杂的版本,主要用于专辑,这个是轻奢型的,用于单曲。一切可以自己定制。 红影 发表于 2024-12-8 14:10
非常清晰的每一步设置。感觉按钮的小三角有点靠左了点,当然从数值设置上没问题呢,可能是误觉。
看两个竖 ...
这是一头大一头小的视觉效果 花飞飞 发表于 2024-12-8 17:31
老师还给了源码,里面显示之前单独封起来的CSS和JS文件。。
这个对小白来说太棒了,很是友好。。 ...
这相当于给个原形。当然,里面的设置和算法还不够严谨。 花飞飞 发表于 2024-12-8 17:26
这个小播长得可俊了。。
背景渐变色彩变化有点立体的感觉。。。
按纽进度条时间显示十分全面。。
这是老朋友了 小辣椒 发表于 2024-12-8 13:36
这个带进度条和小频谱的播放器
{:4_181:} 醉美水芙蓉 发表于 2024-12-8 15:19
老师这个小播也漂亮的!
{:4_190:} 红影 发表于 2024-12-8 14:12
有漂亮的小播,还有进度条和频谱,还有名字展示。很完美
{:4_190:} 红影 发表于 2024-12-8 14:14
好像评分后需要刷新才能自动播放,记得以前把js里的内容包裹起来就不受影响了?
用 var 取代所有的 const 和 let 就可以了 马黑黑 发表于 2024-12-8 19:32
前面那个是复杂的版本,主要用于专辑,这个是轻奢型的,用于单曲。一切可以自己定制。
{:4_173:}轻奢小播,这名字好听。。
可以定制呀,那回头找那个透明的参照一下