|
@@ -1,4 +1,4 @@
|
|
|
-import { defineComponent, reactive, onMounted } from "vue";
|
|
|
+import { defineComponent, reactive, onMounted, computed } from "vue";
|
|
|
import tockAndTick from "/src/constant/tockAndTick.json";
|
|
|
import { Howl } from "howler";
|
|
|
import { Popup } from "vant";
|
|
@@ -9,17 +9,24 @@ import tickWav from "/src/assets/tick.mp3";
|
|
|
import tockWav from "/src/assets/tock.mp3";
|
|
|
|
|
|
const tickData = reactive({
|
|
|
- list: [] as number[],
|
|
|
len: 0,
|
|
|
+ reduceLen: 0,
|
|
|
tickEnd: false,
|
|
|
/** 节拍器时间 */
|
|
|
beatLengthInMilliseconds: 0,
|
|
|
- state: "",
|
|
|
- source1: "" as unknown as Howl,
|
|
|
- source2: "" as unknown as Howl,
|
|
|
index: 0,
|
|
|
- show: false,
|
|
|
+ show: false
|
|
|
});
|
|
|
+
|
|
|
+// 是否使用系统节拍器
|
|
|
+const isUseSystemBeat = computed(()=>{
|
|
|
+ return (state.playType === "play"&& !state.isOpenMetronome)||(state.playType === "sing" && !state.isSingOpenMetronome)
|
|
|
+})
|
|
|
+// 使用哪个节拍器个数
|
|
|
+const useLen = computed(()=>{
|
|
|
+ return isUseSystemBeat.value ? tickData.reduceLen : tickData.len
|
|
|
+})
|
|
|
+
|
|
|
let _time: NodeJS.Timeout
|
|
|
// 关闭节拍器
|
|
|
export function closeTick(){
|
|
@@ -37,11 +44,11 @@ const handlePlay = (i: number, source: any | null) => {
|
|
|
return
|
|
|
};
|
|
|
tickData.index++;
|
|
|
- if (source) {
|
|
|
+ // 当系统节拍器才播放声音
|
|
|
+ if (source && isUseSystemBeat.value) {
|
|
|
const beatVolume = state.setting.beatVolume / 100
|
|
|
source.volume = beatVolume;
|
|
|
- // 当mp3节拍器的时候不播放声音
|
|
|
- if (source.volume <= 0 || state.isOpenMetronome || state.isSingOpenMetronome) {
|
|
|
+ if (source.volume <= 0) {
|
|
|
source.muted = true
|
|
|
} else {
|
|
|
source.muted = false
|
|
@@ -73,13 +80,15 @@ const createAudio = (src: string): Promise<HTMLAudioElement | null> => {
|
|
|
};
|
|
|
|
|
|
/** 设置节拍器
|
|
|
- * @param beatLengthInMilliseconds 节拍间隔时间
|
|
|
* @param beat 节拍数
|
|
|
*/
|
|
|
-export const handleInitTick = (beatLengthInMilliseconds: number, beat: number) => {
|
|
|
- tickData.state = "";
|
|
|
- tickData.beatLengthInMilliseconds = beatLengthInMilliseconds
|
|
|
+export const handleInitTick = (beat: number) => {
|
|
|
tickData.len = beat;
|
|
|
+ // 节拍器的个数除以2 直到小于等于4为止
|
|
|
+ while (beat > 4 && beat % 2 === 0) {
|
|
|
+ beat = beat / 2;
|
|
|
+ }
|
|
|
+ tickData.reduceLen = beat
|
|
|
};
|
|
|
|
|
|
/** 开始节拍器 */
|
|
@@ -87,27 +96,13 @@ export const handleInitTick = (beatLengthInMilliseconds: number, beat: number) =
|
|
|
export const handleStartTick = async () => {
|
|
|
tickData.show = true;
|
|
|
tickData.tickEnd = false;
|
|
|
- if (tickData.state !== "ok") {
|
|
|
- // tickData.source1 = new Howl({
|
|
|
- // src: tockAndTick.tick,
|
|
|
- // // 如果是ios手机,需要强制使用audio,不然部分系统版本第一次播放没有声音
|
|
|
- // html5: browserInfo.ios,
|
|
|
- // });
|
|
|
-
|
|
|
- // tickData.source2 = new Howl({
|
|
|
- // src: tockAndTick.tock,
|
|
|
- // });
|
|
|
- tickData.state = "ok";
|
|
|
- }
|
|
|
tickData.index = 0;
|
|
|
tickData.beatLengthInMilliseconds = (60 / state.speed) * 1000;
|
|
|
- for(let i = 0; i <= tickData.len; i++){
|
|
|
+ for(let i = 0; i <= useLen.value; i++){
|
|
|
// 提前结束, 直接放回false
|
|
|
if (tickData.tickEnd) return false;
|
|
|
- // Howl 插件播放音频
|
|
|
- // const source = i === 0 ? tickData.source1 : i === tickData.len ? null : tickData.source2;
|
|
|
// Audio 标签播放音频
|
|
|
- const source = i === 0 ? audioData.tick : i === tickData.len ? null : audioData.tock;
|
|
|
+ const source = i === 0 ? audioData.tick : i === useLen.value ? null : audioData.tock;
|
|
|
await handlePlay(i, source)
|
|
|
}
|
|
|
tickData.show = false;
|
|
@@ -150,8 +145,8 @@ export default defineComponent({
|
|
|
tickData.show &&
|
|
|
<div class={styles.dots} style={posObj}>
|
|
|
{
|
|
|
- Array.from({ length: tickData.len }).map((item,index)=>{
|
|
|
- return <div class={[styles.dot,((tickData.len - tickData.index)<=index)&&styles.hide]}></div>
|
|
|
+ Array.from({ length: useLen.value }).map((item,index)=>{
|
|
|
+ return <div class={[styles.dot,((useLen.value - tickData.index)<=index)&&styles.hide]}></div>
|
|
|
})
|
|
|
}
|
|
|
</div>
|