Browse Source

一次加载所有的音符音频

liushengqiang 1 năm trước cách đây
mục cha
commit
c685e387ec
4 tập tin đã thay đổi với 81 bổ sung53 xóa
  1. 0 21
      src/pc/component/keys/index.tsx
  2. 25 21
      src/pc/home/index.tsx
  3. 41 1
      src/pc/home/noteData.ts
  4. 15 10
      src/pc/home/runtime.ts

+ 0 - 21
src/pc/component/keys/index.tsx

@@ -30,7 +30,6 @@ export default defineComponent({
 		};
 
 		const keyDown = (e: KeyboardEvent) => {
-			console.log("🚀 ~ e:", e);
 			data.keyDown = e.key.toLocaleUpperCase();
 		};
 		const keyUp = (e: KeyboardEvent) => {
@@ -94,26 +93,6 @@ export default defineComponent({
 									</div>
 								);
 							})}
-							{/* <div
-								class={styles.bkey}
-								onClick={() => {
-									// emit("click", { type: "note", value: item.key + productKey(index - 3) });
-								}}
-							>
-								<div class="keytip"></div>
-							</div>
-							<div class={styles.bkey}>
-								<div class="keytip"></div>
-							</div>
-							<div class={styles.bkey}>
-								<div class="keytip"></div>
-							</div>
-							<div class={styles.bkey}>
-								<div class="keytip"></div>
-							</div>
-							<div class={styles.bkey}>
-								<div class="keytip"></div>
-							</div> */}
 						</div>
 					</div>
 				))}

+ 25 - 21
src/pc/home/index.tsx

@@ -50,6 +50,7 @@ import TheSetting from "./component/the-setting";
 import { useRoute } from "vue-router";
 import { api_musicSheetCreationDetail, api_musicSheetCreationUpdate } from "../api";
 import instrumentsNames from "/src/constant/instrmentsNames.json";
+import { ALL_NOTES, NOTE_DOT } from "./noteData";
 
 const allPitches = [
 	"C,,,,",
@@ -295,6 +296,7 @@ export default defineComponent({
 			midiBuffer: null as unknown as ABCJS.MidiBuffer,
 			abcOptions: {
 				selectionColor: "#0f81ff",
+				jazzchords: true,
 				add_classes: true,
 				clickListener: clickListener,
 				responsive: "resize",
@@ -411,14 +413,24 @@ export default defineComponent({
 			},
 		};
 
-		const resetMidi = (useActive = false) => {
+		const staffNotes = ALL_NOTES();
+		const loadMiniMp3 = async () => {
 			data.loadingAudioSrouce = true;
 			const midiBuffer = new ABCJS.synth.CreateSynth();
-			// console.log(midiBuffer);
+			const str = `X: 1\nM:4/4\nL:1/4\n${staffNotes}`;
+			const visualObj = ABCJS.parseOnly(str);
+			await midiBuffer.init({
+				visualObj: visualObj[0],
+				options: { ...abcData.synthOptions },
+			});
+		};
+
+		const resetMidi = (useActive = false) => {
+			const midiBuffer = new ABCJS.synth.CreateSynth();
 			midiBuffer
 				.init({
 					visualObj: abcData.visualObj,
-					options: { ...abcData.synthOptions, midiTranspose: abcData.abc.visualTranspose },
+					options: { ...abcData.synthOptions },
 				})
 				.then(() => {
 					abcData.synthControl
@@ -873,7 +885,8 @@ export default defineComponent({
 				const activeNote =
 					abcData.abc.measures[data.active.measureIndex]?.notes[data.active.noteIndex] || null;
 				if (!activeNote) return;
-				activeNote.dot = activeNote.dot ? "" : value;
+				activeNote.dot = activeNote.dot ? "" : NOTE_DOT[activeNote.noteType];
+				console.log("🚀 ~ activeNote:", activeNote)
 				await handleResetRender();
 				rangeHighlight(data.active.startChar);
 			}
@@ -1024,7 +1037,6 @@ export default defineComponent({
 			await handleResetRender();
 			const _abcElem = rangeHighlight(data.active.startChar);
 			if (!_abcElem?.midiPitches) return;
-			console.log(_abcElem, abcData.visualObj.millisecondsPerMeasure());
 			ABCJS.synth.playEvent(_abcElem.midiPitches, _abcElem.midiGraceNotePitches, 1000);
 		};
 
@@ -1079,7 +1091,7 @@ export default defineComponent({
 					const _instruments = ABCJS.synth.instrumentIndexToName.indexOf(abcData.abc.subjectCode as any);
 					abcData.synthOptions.program = _instruments > -1 ? _instruments : 0;
 					abcData.abc.measures = abc.measures || initMusic(30);
-					console.log("🚀 ~ abcData.abc:", abcData.abc);
+					// console.log("🚀 ~ abcData.abc:", abcData.abc);
 				}
 			}
 		};
@@ -1097,8 +1109,10 @@ export default defineComponent({
 		};
 		onMounted(async () => {
 			await getDetailData();
+			loadMiniMp3();
 			if (ABCJS.synth.supportsAudio()) {
 				abcData.synthControl = new ABCJS.synth.SynthController();
+				// console.log("🚀 ~ abcData.synthControl:", abcData.synthControl)
 				abcData.synthControl.load("#audio", cursorControl, {
 					displayLoop: true,
 					displayRestart: true,
@@ -1116,8 +1130,8 @@ export default defineComponent({
 					e.returnValue = "还有没保存的";
 				}
 			};
-
-			formateAbc(abcData.visualObj);
+			abcData.synthControl.restart();
+			// formateAbc(abcData.visualObj);
 		});
 		onUnmounted(() => {
 			document.removeEventListener("keyup", handleKeyUp);
@@ -1474,9 +1488,10 @@ export default defineComponent({
 											filterable
 											options={instruments.value}
 											v-model:value={abcData.synthOptions.program}
-											onUpdate:value={() => {
+											onUpdate:value={async () => {
 												abcData.synthControl.disable(true);
 												data.playState = false;
+												await loadMiniMp3();
 												resetMidi(true);
 												popup.selectSubjectShow = false;
 											}}
@@ -2044,18 +2059,7 @@ export default defineComponent({
 						<div id="paper"></div>
 						<Keys show={data.active ? true : false} onClick={(val) => handleChange(val)} />
 
-						{/* <div>
-							<textarea
-								ref={textAreaRef}
-								class={styles.value}
-								id="abc"
-								onChange={() => {
-									console.log(textAreaRef.value.value);
-									data.music = textAreaRef.value.value;
-									handleResetRender();
-								}}
-							></textarea>
-						</div> */}
+						{/* <textarea ref={textAreaRef} class={styles.value} id="abc"></textarea> */}
 						<div id="audio" style={{ opacity: 0 }}></div>
 						<div id="warnings"></div>
 

+ 41 - 1
src/pc/home/noteData.ts

@@ -1,5 +1,35 @@
+export const ALL_NOTES = () => {
+	const keys = ["C", "^C", "D", "^D", "E", "F", "^F", "G", "^G", "A", "^A", "B"];
+	const notes = [];
+	const productKey = (total = 0) => {
+		if (total === 0) return "";
+		return new Array(Math.abs(total)).fill(total > 0 ? "'" : ",").join("");
+	};
+	for (let i = 0; i <= 6; i++) {
+		for (let j = 0; j < 12; j++) {
+			let note = keys[j];
+			if (i < 3) {
+				notes.push(note + productKey(i - 3));
+			} else if (i === 3) {
+				notes.push(note);
+			} else if (i === 4) {
+				note = note.toLocaleLowerCase();
+				notes.push(note);
+			} else {
+				note = note.toLocaleLowerCase();
+				notes.push(note + productKey(i - 4));
+			}
+		}
+	}
+	let str = "";
+	notes.forEach((note, index) => {
+		str += note + (index % 4 === 0 ? " |" : " ");
+	});
+	// console.log(notes);
+	return str;
+};
 export const ABC_NOTE_DATA = [
-	["^B,,,,,", "C,,,,"],
+	"C,,,,",
 	["^C,,,,", "_D,,,,"],
 	"D,,,,",
 	["^D,,,,", "_E,,,,"],
@@ -356,3 +386,13 @@ export const ABC_KEYS: { [_: string]: any } = {
 		"K:B": { up: 0, down: 0, move: 0 },
 	},
 };
+
+/** 附点音符 */
+export const NOTE_DOT: { [_: string]: string } = {
+	"4": "3",
+	"2": "3",
+	"": "3/2",
+	"/": "2/3",
+	"//": "1/3",
+	"///": "3/8",
+};

+ 15 - 10
src/pc/home/runtime.ts

@@ -213,8 +213,12 @@ export const renderMeasures = (abc: IAbc) => {
 			text += note.dynamics; // 力度符号
 			text += note.accidental; // 临时升降记号
 			text += note.content; // 音符
-			text += note.noteType; // 音符类型
-			text += note.dot; // 附点
+			// 音符时值
+			if(note.dot){
+				text += note.dot; // 附点
+			} else {
+				text += note.noteType; // 音符类型
+			}
 			text += note.tieline; // 延音
 			if (note.tie.includes(")")) {
 				// 连音线 后
@@ -222,8 +226,9 @@ export const renderMeasures = (abc: IAbc) => {
 			}
 			text += note.segno; // 分割
 		}
+		let _i = i + 1;
+		// text += `${_i % 4 !== 0 ? `"${i + 1}"` : ""}${i === measures.length - 1 ? '|]' : measure.barline}`;
 		text += measure.barline;
-		// text += `"${i}"` + measure.barline;
 		if (i > 0 && i % 4 === 0) {
 			text += "\n";
 		}
@@ -286,14 +291,14 @@ export const formateAbc = (visualObj: TuneObject) => {
 		if (line.staff) {
 			for (let j = 0; j < line.staff.length; j++) {
 				const staff = line.staff[j];
-				if (i === 0){
-					if (staff.clef){
+				if (i === 0) {
+					if (staff.clef) {
 						abc.celf = `K:${staff.clef.type}`;
 					}
-					if (staff.key){
+					if (staff.key) {
 						abc.key = `K:${staff.key.root}${staff.key.acc}`;
 					}
-					if (staff.meter?.value?.[0]){
+					if (staff.meter?.value?.[0]) {
 						abc.meter = `M:${staff.meter.value[0].num}/${staff.meter.value[0].den}`;
 					}
 				}
@@ -302,8 +307,8 @@ export const formateAbc = (visualObj: TuneObject) => {
 						const voice = staff.voices[k];
 						for (let l = 0; l < voice.length; l++) {
 							const element = voice[l];
-							if (element.el_type === "bar"){
-								measureIndex++
+							if (element.el_type === "bar") {
+								measureIndex++;
 							}
 							if (element.el_type === "note") {
 								list.push(element);
@@ -314,5 +319,5 @@ export const formateAbc = (visualObj: TuneObject) => {
 			}
 		}
 	}
-	console.log(measureIndex)
+	console.log(measureIndex);
 };