样式如图 主要实现拖拽事件,支持移动端、PC端
<div class="progress-wrapper">
<p class="time-text">2:25</p>
<div
ref="progress"
class="progress-bar van-progress"
style="height: 2px;"
>
<span
class="van-progress__portion"
:style="`width: ${positionX}px;`"
>
<span
class="van-progress__pivot play-dot"
:style="`left: ${positionX}px;`"
@mousedown="down"
@touchstart.stop="down"
@mousemove="move"
@touchmove.stop="move"
@mouseup="end"
@touchend.stop="end"
>
<span class="solid-dot"></span
></span>
</span>
</div>
<p class="time-text">104:50</p>
</div>
拖拽函数
// 鼠标位置和div的左上角位置 差值
var dx, maxWidth;
// 当前长度px 总长度px 计算要切到的时间点
setProgStyle(current, total) {
let percent = (current / total) * 10000;
percent = Math.round(percent) / 100 + "%";
// console.log("进度条", percent);
// let curTime = (current / total) * this.liveInfo.duration;
},
// 实现移动端拖拽
down() {
this.flags = true;
maxWidth = this.$refs.progress.offsetWidth;
// 总的进度条与屏幕左侧的距离
dx = this.$refs.progress.offsetLeft;
},
move(event) {
if (this.flags) {
var touch;
if (event.touches) {
touch = event.touches[0];
} else {
touch = event;
}
// 定位滑块的位置
this.positionX = touch.clientX - dx;
// 限制滑块超出页面
// 最大值screenWidth - touch.target.clientWidth, 改为this.$refs.progress.offsetWidth
if (this.positionX < 0) {
this.positionX = 0;
} else if (this.positionX > maxWidth) {
this.positionX = maxWidth; // 308
}
this.setProgStyle(this.positionX, maxWidth);
// 阻止页面的滑动默认事件
document.addEventListener(
"touchmove",
function() {
event.preventDefault();
},
false
);
}
},
//鼠标释放时候的函数
end() {
// 范围大概是0~308
console.log("end", this.positionX);
this.flags = false;
}
样式 SCSS
.progress-wrapper {
padding: 0 0.25rem;
width: 100%;
height: 1rem;
box-sizing: border-box;
display: flex;
justify-content: center;
align-items: center;
.time-text {
max-width: 0.8rem;
font-size: 0.26rem;
}
.progress-bar {
position: relative;
margin: 0 0.2rem;
width: 6rem;
height: 2px;
background: rgba(#e0dfdf, 0.5); // #c4c2c2
border-radius: 4px;
.van-progress__portion {
position: absolute;
left: 0;
height: 100%;
background: #e0dfdf;
border-radius: inherit;
.play-dot {
position: absolute;
top: 50%;
box-sizing: border-box;
padding: 0 5px;
color: #fff;
font-size: 10px;
line-height: 1.6;
text-align: center;
word-break: keep-all;
background-color: #1989fa;
border-radius: 1em;
-webkit-transform: translate(-50%, -50%);
transform: translate(-50%, -50%);
width: 20px;
min-width: 0;
height: 20px;
background: rgba(#2788ff, 0.3);
border-radius: 50%;
display: flex;
justify-content: center;
align-items: center;
.solid-dot {
width: 10px;
height: 10px;
background: #0489f5;
border-radius: 50%;
}
}
}
}
}