预计实现效果
子组件
<template>
<div class="_base-count-down no-rtl">
<div class="content">
<slot v-bind="{
d: days, h: hours, m: mins, s: seconds,
hh: `00${hours}`.slice(-2),
mm: `00${mins}`.slice(-2),
ss: `00${seconds}`.slice(-2),
}"></slot>
</div>
</div>
</template>
<script>
export default {
data: () => ({
days: '0',
hours: '00',
mins: '00',
seconds: '00',
timer: null,
curTime: 0
}),
props: {
// 倒计时长
time: {
type: [Number, String],
default: 0
},
// 刷新计数器
refreshCounter: {
type: [Number, String],
default: 0
},
// 倒计时技术时间
end: {
type: [Number, String],
default: 0
},
// 秒还是毫秒单位
isMiniSecond: {
type: Boolean,
default: false
}
},
computed: {
duration() {
if (this.end) {
let end = String(this.end).length >= 13 ? +this.end : +this.end * 1000
end -= Date.now()
return end
}
// +统一转换为number类型
const time = this.isMiniSecond ? Math.round(+this.time / 1000) : Math.round(+this.time)
return time
}
},
mounted() {
this.countDown()
},
watch: {
duration() {
this.countDown()
},
refreshCounter() {
this.countDown()
}
},
methods: {
// 转换时间格式
durationFormatter(time) {
if (!time) return { ss: 0 }
let t = time
const ss = t % 60
t = (t - ss) / 60
if (t < 1) return { ss }
const mm = t % 60
t = (t - mm) / 60
if (t < 1) return { mm, ss }
const hh = t % 24
t = (t - hh) / 24
if (t < 1) return { hh, mm, ss }
const dd = t
return { dd, hh, mm, ss }
},
countDown() {
this.curTime = Date.now()
this.getTime(this.duration)
},
getTime(time) {
this.timer && clearTimeout(this.timer)
if (time < 0) {
return
}
const { dd, hh, mm, ss } = this.durationFormatter(time)
this.days = dd || 0
this.hours = hh || 0
this.mins = mm || 0
this.seconds = ss || 0
this.timer = setTimeout(() => {
const now = Date.now()
const diffTime = Math.floor((now - this.curTime) / 1000)
const step = diffTime > 1 ? diffTime : 1 // 页面退到后台的时候不会计时,对比时间差,大于1s的重置倒计时
this.curTime = now
this.getTime(time - step)
}, 1000)
}
}
};
</script>
<style lang='less' scoped>
._base-count-down {
color: #000;
text-align: left;
position: relative;
.content {
width: auto;
display: flex;
align-items: center;
}
span {
display: inline-block;
}
.section {
position: relative;
}
}
</style>
怎么使用
<ergo-active-countdown v-slot="timeObj" :time="countDown">
<div class="count-down">
<div class="icon"></div>
{{timeObj.d}}天{{timeObj.hh}}小时{{timeObj.mm}}分钟{{timeObj.ss}}秒
</div>
</ergo-active-countdown>
import mainBottomCom from '@/components/MainButtomCom/Index'
components:{
ErgoActiveCountdown
}
倒计时组件就完成了