feat:1. 调整项目结构,将API接口定义单独抽离 2. 将倒计时计算逻辑调整到后端进行处理计算 3. 增加铃声提示功能
This commit is contained in:
@@ -0,0 +1,99 @@
|
||||
// src/composables/useTimer.ts
|
||||
import { ref } from 'vue';
|
||||
import { ElMessageBox, ElMessage } from 'element-plus';
|
||||
|
||||
export function useTimer(audioUrl: string = '/public/resource/notification.mp3') {
|
||||
const timerMinutes = ref(25);
|
||||
const timerSeconds = ref(0);
|
||||
const remainingTime = ref(25 * 60 * 1000);
|
||||
const timerRunning = ref(false);
|
||||
const timerIsOver = ref(false);
|
||||
const audioActivated = ref(false);
|
||||
|
||||
let timerInterval: number;
|
||||
const audio = new Audio(audioUrl);
|
||||
|
||||
const clear = () => {
|
||||
clearInterval(timerInterval);
|
||||
timerRunning.value = false;
|
||||
};
|
||||
|
||||
const handleCountdownComplete = () => {
|
||||
audio.loop = true;
|
||||
audio.play();
|
||||
ElMessageBox.alert('本次番茄钟结束!请点击“休息”按钮开始休息倒计时', '提醒', {
|
||||
confirmButtonText: '关闭铃声',
|
||||
callback: () => {
|
||||
audio.pause();
|
||||
audio.currentTime = 0;
|
||||
ElMessage.success('铃声已关闭');
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
const runCountdown = (durationMs: number, onComplete: () => void = handleCountdownComplete) => {
|
||||
clearInterval(timerInterval);
|
||||
const endTimeStamp = Date.now() + durationMs;
|
||||
remainingTime.value = durationMs;
|
||||
timerIsOver.value = false;
|
||||
timerRunning.value = true;
|
||||
|
||||
timerInterval = window.setInterval(() => {
|
||||
const now = Date.now();
|
||||
remainingTime.value = Math.max(endTimeStamp - now, 0);
|
||||
timerMinutes.value = Math.floor(remainingTime.value / 1000 / 60);
|
||||
timerSeconds.value = Math.floor((remainingTime.value / 1000) % 60);
|
||||
|
||||
if (remainingTime.value === 0 && !timerIsOver.value) {
|
||||
timerIsOver.value = true;
|
||||
timerRunning.value = false;
|
||||
onComplete();
|
||||
}
|
||||
}, 1000);
|
||||
};
|
||||
|
||||
const checkAudioPermission = async () => {
|
||||
try {
|
||||
await audio.play();
|
||||
audio.pause();
|
||||
audio.currentTime = 0;
|
||||
audioActivated.value = true;
|
||||
return true;
|
||||
} catch {
|
||||
audioActivated.value = false;
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
const requestAudioPermission = () => {
|
||||
return new Promise<boolean>((resolve) => {
|
||||
ElMessageBox.alert('点击确认激活提示音权限。', '权限激活', {
|
||||
confirmButtonText: '确认',
|
||||
callback: async () => {
|
||||
try {
|
||||
await audio.play();
|
||||
audio.pause();
|
||||
audio.currentTime = 0;
|
||||
audioActivated.value = true;
|
||||
resolve(true);
|
||||
} catch {
|
||||
resolve(false);
|
||||
}
|
||||
},
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
return {
|
||||
timerMinutes,
|
||||
timerSeconds,
|
||||
remainingTime,
|
||||
timerRunning,
|
||||
timerIsOver,
|
||||
runCountdown,
|
||||
clear,
|
||||
checkAudioPermission,
|
||||
requestAudioPermission,
|
||||
audioActivated,
|
||||
};
|
||||
}
|
||||
Reference in New Issue
Block a user