|
@@ -40,6 +40,7 @@ import {
|
|
NSelect,
|
|
NSelect,
|
|
NSpace,
|
|
NSpace,
|
|
NSpin,
|
|
NSpin,
|
|
|
|
+ useDialog,
|
|
useMessage,
|
|
useMessage,
|
|
} from "naive-ui";
|
|
} from "naive-ui";
|
|
import { LongArrowAltDown, LongArrowAltUp, GripLinesVertical } from "@vicons/fa";
|
|
import { LongArrowAltDown, LongArrowAltUp, GripLinesVertical } from "@vicons/fa";
|
|
@@ -56,6 +57,7 @@ import { UseDraggable } from "@vueuse/components";
|
|
import { getQuery } from "/src/utils/queryString";
|
|
import { getQuery } from "/src/utils/queryString";
|
|
import Metronome, { metronomeData } from "/src/helpers/metronome";
|
|
import Metronome, { metronomeData } from "/src/helpers/metronome";
|
|
import cleanDeep from "clean-deep";
|
|
import cleanDeep from "clean-deep";
|
|
|
|
+import { saveAs } from "file-saver";
|
|
|
|
|
|
export const initMusic = (total: number): IMeasure[] => {
|
|
export const initMusic = (total: number): IMeasure[] => {
|
|
return new Array(total).fill(0).map((item, index) => {
|
|
return new Array(total).fill(0).map((item, index) => {
|
|
@@ -102,6 +104,7 @@ function moveNote(note: string, step: number) {
|
|
export default defineComponent({
|
|
export default defineComponent({
|
|
name: "Home",
|
|
name: "Home",
|
|
setup() {
|
|
setup() {
|
|
|
|
+ const dialog = useDialog();
|
|
const route = useRoute();
|
|
const route = useRoute();
|
|
const message = useMessage();
|
|
const message = useMessage();
|
|
const popup = reactive({
|
|
const popup = reactive({
|
|
@@ -621,11 +624,22 @@ export default defineComponent({
|
|
|
|
|
|
if (type === "exit") {
|
|
if (type === "exit") {
|
|
if (!data.isSave) {
|
|
if (!data.isSave) {
|
|
- showConfirmDialog({
|
|
|
|
|
|
+ dialog.warning({
|
|
|
|
+ maskClosable: true,
|
|
|
|
+ autoFocus: false,
|
|
|
|
+ class: "deleteDialog saveDialog",
|
|
title: "温馨提示",
|
|
title: "温馨提示",
|
|
- message: "还没保存,是否保存?",
|
|
|
|
- })
|
|
|
|
- .then(async () => {
|
|
|
|
|
|
+ content: "是否保存当前曲谱?",
|
|
|
|
+ positiveText: "保存",
|
|
|
|
+ positiveButtonProps: {
|
|
|
|
+ type: "primary",
|
|
|
|
+ },
|
|
|
|
+ negativeText: "不保存",
|
|
|
|
+ negativeButtonProps: {
|
|
|
|
+ type: "default",
|
|
|
|
+ ghost: false,
|
|
|
|
+ },
|
|
|
|
+ onPositiveClick: async () => {
|
|
const msg = message.loading("保存中...");
|
|
const msg = message.loading("保存中...");
|
|
await handleSaveMusic(false);
|
|
await handleSaveMusic(false);
|
|
setTimeout(() => {
|
|
setTimeout(() => {
|
|
@@ -636,10 +650,11 @@ export default defineComponent({
|
|
handleClose();
|
|
handleClose();
|
|
}, 500);
|
|
}, 500);
|
|
}, 300);
|
|
}, 300);
|
|
- })
|
|
|
|
- .catch(() => {
|
|
|
|
|
|
+ },
|
|
|
|
+ onNegativeClick: () => {
|
|
handleClose();
|
|
handleClose();
|
|
- });
|
|
|
|
|
|
+ },
|
|
|
|
+ });
|
|
return;
|
|
return;
|
|
}
|
|
}
|
|
handleClose();
|
|
handleClose();
|
|
@@ -1005,7 +1020,7 @@ export default defineComponent({
|
|
|
|
|
|
// 移动音符
|
|
// 移动音符
|
|
if (type === "move") {
|
|
if (type === "move") {
|
|
- const step = value._step ? value._step : value.action === "up" ? -1 : 1;
|
|
|
|
|
|
+ const step = value.action === "drag" ? value.step : value.action === "up" ? -1 : 1;
|
|
if (!activeNote) return;
|
|
if (!activeNote) return;
|
|
activeNote.content = moveNote(activeNote.content, step);
|
|
activeNote.content = moveNote(activeNote.content, step);
|
|
// arr now contains elements that are either a chord, a decoration, a note name, or anything else. It can be put back to its original string with .join("").
|
|
// arr now contains elements that are either a chord, a decoration, a note name, or anything else. It can be put back to its original string with .join("").
|
|
@@ -1210,6 +1225,7 @@ export default defineComponent({
|
|
}
|
|
}
|
|
}
|
|
}
|
|
data.loading = false;
|
|
data.loading = false;
|
|
|
|
+ return res;
|
|
};
|
|
};
|
|
const handleSaveMusic = async (tips = true) => {
|
|
const handleSaveMusic = async (tips = true) => {
|
|
await api_musicSheetCreationUpdate({
|
|
await api_musicSheetCreationUpdate({
|
|
@@ -1397,6 +1413,20 @@ export default defineComponent({
|
|
}
|
|
}
|
|
};
|
|
};
|
|
|
|
|
|
|
|
+ const downXML = async () => {
|
|
|
|
+ const msg = message.loading("导出中...");
|
|
|
|
+ await handleSaveMusic(false);
|
|
|
|
+ const res = await getDetailData();
|
|
|
|
+ if (!res?.data?.xml) {
|
|
|
|
+ msg.type = "error";
|
|
|
|
+ msg.content = "导出失败";
|
|
|
|
+ return;
|
|
|
|
+ }
|
|
|
|
+ saveAs(res.data.xml, (data.musicName || '曲谱') + ".xml");
|
|
|
|
+ msg.type = "success";
|
|
|
|
+ msg.content = "导出成功";
|
|
|
|
+ };
|
|
|
|
+
|
|
const handleDownFile = (type: IFileBtnType) => {
|
|
const handleDownFile = (type: IFileBtnType) => {
|
|
if (type === "png") {
|
|
if (type === "png") {
|
|
downPng();
|
|
downPng();
|
|
@@ -1404,6 +1434,8 @@ export default defineComponent({
|
|
downMidi();
|
|
downMidi();
|
|
} else if (type === "wav") {
|
|
} else if (type === "wav") {
|
|
downWav();
|
|
downWav();
|
|
|
|
+ } else if (type === "down-xml") {
|
|
|
|
+ downXML();
|
|
}
|
|
}
|
|
};
|
|
};
|
|
|
|
|
|
@@ -1413,6 +1445,7 @@ export default defineComponent({
|
|
input.accept = ".xml,.musicxml";
|
|
input.accept = ".xml,.musicxml";
|
|
input.onchange = (e: any) => {
|
|
input.onchange = (e: any) => {
|
|
const file = e.target.files[0];
|
|
const file = e.target.files[0];
|
|
|
|
+
|
|
const reader = new FileReader();
|
|
const reader = new FileReader();
|
|
reader.onload = (e: any) => {
|
|
reader.onload = (e: any) => {
|
|
let abc = e.target.result;
|
|
let abc = e.target.result;
|
|
@@ -1487,7 +1520,7 @@ export default defineComponent({
|
|
} else if (["xml"].includes(val)) {
|
|
} else if (["xml"].includes(val)) {
|
|
handleExport();
|
|
handleExport();
|
|
} else if (val === "upload") {
|
|
} else if (val === "upload") {
|
|
- } else if (["png", "midi", "wav"].includes(val)) {
|
|
|
|
|
|
+ } else if (["png", "midi", "wav", "down-xml"].includes(val)) {
|
|
handleDownFile(val);
|
|
handleDownFile(val);
|
|
} else if (val === "print") {
|
|
} else if (val === "print") {
|
|
}
|
|
}
|
|
@@ -2301,7 +2334,7 @@ export default defineComponent({
|
|
)}
|
|
)}
|
|
|
|
|
|
{/* <textarea ref={textAreaRef} class={styles.value} id="abc"></textarea> */}
|
|
{/* <textarea ref={textAreaRef} class={styles.value} id="abc"></textarea> */}
|
|
- <div id="importRef"></div>
|
|
|
|
|
|
+ <div id="importRef" style={{ display: "none" }}></div>
|
|
<div id="audio" style={{ display: "none" }}></div>
|
|
<div id="audio" style={{ display: "none" }}></div>
|
|
{data.loadingAudioSrouce && (
|
|
{data.loadingAudioSrouce && (
|
|
<div class={styles.loading}>
|
|
<div class={styles.loading}>
|