<!--倒计时
使用说明:传入time(时间差 秒)
-->
<template>
<div class="countdown">
<slot v-if="format" :time="formatCountdown(timeDiff)"></slot>
<slot v-else :time="timeDiff"></slot>
</div>
</template>
<script>
export default {
props: {
// 时间差
time: {
type: Number,
default: 60
},
// 步长
step: {
type: Number,
default: 1
},
// 开关
switch: {
type: Boolean,
default: null
},
// 格式化
format: {
type: String,
default: ''
}
},
data() {
return {
// 时间函数
timer: null,
// 倒计时
timeDiff: 0
};
},
computed: {
// 步长转换为毫秒
computedStep() {
return this.step * 1000;
}
},
watch: {
// 监听倒计时时间差变化
time: {
handler(val) {
this.timeDiff = val;
const isSwitch = typeof this.switch === 'boolean';
if(val && !this.timer) {
if(isSwitch) {
if(this.switch) {
this.triggerTimer();
} else {
this.clearTimer();
}
} else {
this.triggerTimer();
}
} else {
this.clearTimer();
}
},
immediate: true
},
// 监听开关变化
switch: {
handler(val) {
if(val) {
this.triggerTimer();
} else {
this.clearTimer();
}
}
}
},
methods: {
// 触发倒计时函数
triggerTimer() {
this.timer = setTimeout(() => {
this.timeDiff--;
if(this.timeDiff <= 0) {
this.$emit('on-end');
} else {
this.$emit('on-countdown', this.timeDiff);
this.triggerTimer();
}
}, this.computedStep);
},
// 清除定时器
clearTimer() {
if(this.timer) {
clearTimeout(this.timer);
}
},
// 格式化时间戳
formatCountdown(timeDiff) {
// 获取还剩多少小时
const hour = parseInt((timeDiff / 60 / 60).toString());
// 获取还剩多少分钟
let minute;
if(this.format.includes('hh') || this.format.includes('HH')) {
minute = parseInt(((timeDiff / 60) % 60).toString());
} else {
minute = parseInt((timeDiff / 60).toString());
}
// 获取还剩多少秒
let second;
if(this.format.includes('mm') || this.format.includes('MM')) {
second = timeDiff % 60;
} else {
second = timeDiff;
}
let result = this.format;
result = result.replace(/(hh|HH)/g, this.paddingZero(hour));
result = result.replace(/(mm|MM)/g, this.paddingZero(minute));
result = result.replace(/(ss|SS)/g, this.paddingZero(second));
return result;
},
// 补零
paddingZero(val) {
if(val <= 0) {
return '00';
} else if(val < 10) {
return `0${val}`;
} else {
return val.toString();
}
},
// 重新倒计时
reCountdown() {
this.timeDiff = this.time;
}
},
beforeDestroy() {
this.clearTimer();
}
};
</script>
<style lang="scss" scoped>
.countdown {
display: inline-block;
}
</style>
网友评论