From 1bea37073f305929215bf2c3f28e2263acb6fc20 Mon Sep 17 00:00:00 2001 From: whycq <913841844@qq.com> Date: 星期一, 13 二月 2023 19:53:42 +0800 Subject: [PATCH] # --- uni_modules/uni-countdown/components/uni-countdown/uni-countdown.vue | 271 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 files changed, 271 insertions(+), 0 deletions(-) diff --git a/uni_modules/uni-countdown/components/uni-countdown/uni-countdown.vue b/uni_modules/uni-countdown/components/uni-countdown/uni-countdown.vue new file mode 100644 index 0000000..1f8ef4e --- /dev/null +++ b/uni_modules/uni-countdown/components/uni-countdown/uni-countdown.vue @@ -0,0 +1,271 @@ +<template> + <view class="uni-countdown"> + <text v-if="showDay" :style="[timeStyle]" class="uni-countdown__number">{{ d }}</text> + <text v-if="showDay" :style="[splitorStyle]" class="uni-countdown__splitor">{{dayText}}</text> + <text :style="[timeStyle]" class="uni-countdown__number">{{ h }}</text> + <text :style="[splitorStyle]" class="uni-countdown__splitor">{{ showColon ? ':' : hourText }}</text> + <text :style="[timeStyle]" class="uni-countdown__number">{{ i }}</text> + <text :style="[splitorStyle]" class="uni-countdown__splitor">{{ showColon ? ':' : minuteText }}</text> + <text :style="[timeStyle]" class="uni-countdown__number">{{ s }}</text> + <text v-if="!showColon" :style="[splitorStyle]" class="uni-countdown__splitor">{{secondText}}</text> + </view> +</template> +<script> + import { + initVueI18n + } from '@dcloudio/uni-i18n' + import messages from './i18n/index.js' + const { + t + } = initVueI18n(messages) + /** + * Countdown 鍊掕鏃� + * @description 鍊掕鏃剁粍浠� + * @tutorial https://ext.dcloud.net.cn/plugin?id=25 + * @property {String} backgroundColor 鑳屾櫙鑹� + * @property {String} color 鏂囧瓧棰滆壊 + * @property {Number} day 澶╂暟 + * @property {Number} hour 灏忔椂 + * @property {Number} minute 鍒嗛挓 + * @property {Number} second 绉� + * @property {Number} timestamp 鏃堕棿鎴� + * @property {Boolean} showDay = [true|false] 鏄惁鏄剧ず澶╂暟 + * @property {Boolean} show-colon = [true|false] 鏄惁浠ュ啋鍙蜂负鍒嗛殧绗� + * @property {String} splitorColor 鍒嗗壊绗﹀彿棰滆壊 + * @event {Function} timeup 鍊掕鏃舵椂闂村埌瑙﹀彂浜嬩欢 + * @example <uni-countdown :day="1" :hour="1" :minute="12" :second="40"></uni-countdown> + */ + export default { + name: 'UniCountdown', + emits: ['timeup'], + props: { + showDay: { + type: Boolean, + default: true + }, + showColon: { + type: Boolean, + default: true + }, + start: { + type: Boolean, + default: true + }, + backgroundColor: { + type: String, + default: '' + }, + color: { + type: String, + default: '#333' + }, + fontSize: { + type: Number, + default: 14 + }, + splitorColor: { + type: String, + default: '#333' + }, + day: { + type: Number, + default: 0 + }, + hour: { + type: Number, + default: 0 + }, + minute: { + type: Number, + default: 0 + }, + second: { + type: Number, + default: 0 + }, + timestamp: { + type: Number, + default: 0 + } + }, + data() { + return { + timer: null, + syncFlag: false, + d: '00', + h: '00', + i: '00', + s: '00', + leftTime: 0, + seconds: 0 + } + }, + computed: { + dayText() { + return t("uni-countdown.day") + }, + hourText(val) { + return t("uni-countdown.h") + }, + minuteText(val) { + return t("uni-countdown.m") + }, + secondText(val) { + return t("uni-countdown.s") + }, + timeStyle() { + const { + color, + backgroundColor, + fontSize + } = this + return { + color, + backgroundColor, + fontSize: `${fontSize}px`, + width: `${fontSize * 22 / 14}px`, // 鎸夊瓧浣撳ぇ灏忎负 14px 鏃剁殑姣斾緥缂╂斁 + lineHeight: `${fontSize * 20 / 14}px`, + borderRadius: `${fontSize * 3 / 14}px`, + } + }, + splitorStyle() { + const { splitorColor, fontSize, backgroundColor } = this + return { + color: splitorColor, + fontSize: `${fontSize * 12 / 14}px`, + margin: backgroundColor ? `${fontSize * 4 / 14}px` : '' + } + } + }, + watch: { + day(val) { + this.changeFlag() + }, + hour(val) { + this.changeFlag() + }, + minute(val) { + this.changeFlag() + }, + second(val) { + this.changeFlag() + }, + start: { + immediate: true, + handler(newVal, oldVal) { + if (newVal) { + this.startData(); + } else { + if (!oldVal) return + clearInterval(this.timer) + } + } + + } + }, + created: function(e) { + this.seconds = this.toSeconds(this.timestamp, this.day, this.hour, this.minute, this.second) + this.countDown() + }, + // #ifndef VUE3 + destroyed() { + clearInterval(this.timer) + }, + // #endif + // #ifdef VUE3 + unmounted() { + clearInterval(this.timer) + }, + // #endif + methods: { + toSeconds(timestamp, day, hours, minutes, seconds) { + if (timestamp) { + return timestamp - parseInt(new Date().getTime() / 1000, 10) + } + return day * 60 * 60 * 24 + hours * 60 * 60 + minutes * 60 + seconds + }, + timeUp() { + clearInterval(this.timer) + this.$emit('timeup') + }, + countDown() { + let seconds = this.seconds + let [day, hour, minute, second] = [0, 0, 0, 0] + if (seconds > 0) { + day = Math.floor(seconds / (60 * 60 * 24)) + hour = Math.floor(seconds / (60 * 60)) - (day * 24) + minute = Math.floor(seconds / 60) - (day * 24 * 60) - (hour * 60) + second = Math.floor(seconds) - (day * 24 * 60 * 60) - (hour * 60 * 60) - (minute * 60) + } else { + this.timeUp() + } + if (day < 10) { + day = '0' + day + } + if (hour < 10) { + hour = '0' + hour + } + if (minute < 10) { + minute = '0' + minute + } + if (second < 10) { + second = '0' + second + } + this.d = day + this.h = hour + this.i = minute + this.s = second + }, + startData() { + this.seconds = this.toSeconds(this.timestamp, this.day, this.hour, this.minute, this.second) + if (this.seconds <= 0) { + this.seconds = this.toSeconds(0, 0, 0, 0, 0) + this.countDown() + return + } + clearInterval(this.timer) + this.countDown() + this.timer = setInterval(() => { + this.seconds-- + if (this.seconds < 0) { + this.timeUp() + return + } + this.countDown() + }, 1000) + }, + update(){ + this.startData(); + }, + changeFlag() { + if (!this.syncFlag) { + this.seconds = this.toSeconds(this.timestamp, this.day, this.hour, this.minute, this.second) + this.startData(); + this.syncFlag = true; + } + } + } + } +</script> +<style lang="scss" scoped> + $font-size: 14px; + + .uni-countdown { + display: flex; + flex-direction: row; + justify-content: flex-start; + align-items: center; + + &__splitor { + margin: 0 2px; + font-size: $font-size; + color: #333; + } + + &__number { + border-radius: 3px; + text-align: center; + font-size: $font-size; + } + } +</style> -- Gitblit v1.9.1