Skip to content

Commit f15203d

Browse files
author
liugaowei
committed
重试功能,更新版本
1 parent 9b97253 commit f15203d

File tree

5 files changed

+104
-23
lines changed

5 files changed

+104
-23
lines changed

package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "tts-vue",
3-
"version": "1.9.12",
3+
"version": "1.9.15",
44
"main": "dist/electron/main/index.js",
55
"description": "🎤 微软语音合成工具,使用 Electron + Vue + ElementPlus + Vite 构建。",
66
"author": "沫離Loker <[email protected]>",

src/components/configpage/ConfigPage.vue

+41-4
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
<template>
22
<div class="config-page">
3-
<div class="config-side">
4-
<el-form :model="config" label-position="top">
3+
<div class="config-side" label-position="right">
4+
<el-form :model="config" >
55
<el-form-item label="下载路径">
66
<el-input
77
v-model="config.savePath"
@@ -14,6 +14,24 @@
1414
</template>
1515
</el-input>
1616
</el-form-item>
17+
<el-form-item label="重试次数">
18+
<el-input
19+
type="number"
20+
v-model="config.retryCount"
21+
size="small"
22+
class="input-path"
23+
@change="setRetryCount"
24+
/>
25+
</el-form-item>
26+
<el-form-item label="重试间隔(s)">
27+
<el-input
28+
type="number"
29+
v-model="config.retryInterval"
30+
size="small"
31+
class="input-path"
32+
@change="setRetryInterval"
33+
/>
34+
</el-form-item>
1735
<el-form-item label="SpeechKey">
1836
<el-input
1937
v-model="config.speechKey"
@@ -31,7 +49,7 @@
3149
@change="setServiceRegion"
3250
/>
3351
</el-form-item>
34-
<el-form-item label="自动播放(仅单文本模式)">
52+
<el-form-item label="自动播放">
3553
<el-switch
3654
v-model="config.autoplay"
3755
active-text=""
@@ -40,7 +58,7 @@
4058
@change="switchChange"
4159
/>
4260
</el-form-item>
43-
<el-form-item label="版本更新弹窗提醒">
61+
<el-form-item label="新版本提醒">
4462
<el-switch
4563
v-model="config.updateNotification"
4664
active-text=""
@@ -188,6 +206,7 @@ const savePathConfig = () => {
188206
duration: 2000,
189207
});
190208
};
209+
191210
const auditionConfig = () => {
192211
ttsStore.setAuditionConfig();
193212
ElMessage({
@@ -241,6 +260,24 @@ const setServiceRegion = () => {
241260
duration: 2000,
242261
});
243262
};
263+
264+
const setRetryCount = () => {
265+
ttsStore.setRetryCount();
266+
ElMessage({
267+
message: "保存成功,请点击“刷新配置”立即应用。。",
268+
type: "success",
269+
duration: 2000,
270+
});
271+
};
272+
273+
const setRetryInterval = () => {
274+
ttsStore.setRetryInterval();
275+
ElMessage({
276+
message: "保存成功,请点击“刷新配置”立即应用。。",
277+
type: "success",
278+
duration: 2000,
279+
});
280+
};
244281
</script>
245282

246283
<style scoped>

src/global/initLocalStore.ts

+6
Original file line numberDiff line numberDiff line change
@@ -51,4 +51,10 @@ export default async function initStore() {
5151
if (!store.has("disclaimers")) {
5252
store.set("disclaimers", false);
5353
}
54+
if (!store.has("retryCount")) {
55+
store.set("retryCount", 10);
56+
}
57+
if (!store.has("retryInterval")) {
58+
store.set("retryInterval", 3);
59+
}
5460
}

src/store/play.ts

+23-2
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,9 @@ async function getTTSData(
1111
pitch = 0,
1212
api: number,
1313
key: string,
14-
region: string
14+
region: string,
15+
retryCount: number,
16+
retryInterval = 1,
1517
) {
1618
let SSML = "";
1719
if (inps.activeIndex == "1" && (api == 1 || api == 3)) {
@@ -46,7 +48,7 @@ async function getTTSData(
4648
ipcRenderer.send("log.info", SSML);
4749
console.log(SSML);
4850
if (api == 1) {
49-
const result = await ipcRenderer.invoke("speech", SSML);
51+
const result = await retrySpeechInvocation(SSML, retryCount, retryInterval * 1000);
5052
return result;
5153
} else if (api == 2) {
5254
const result = await ipcRenderer.invoke("edgeApi", SSML);
@@ -56,4 +58,23 @@ async function getTTSData(
5658
return result;
5759
}
5860
}
61+
async function retrySpeechInvocation(SSML: string, retryCount: number, delay: number) {
62+
let retry = 0;
63+
while (retry < retryCount) {
64+
try {
65+
console.log("Speech invocation attempt", retry + 1);
66+
const result = await ipcRenderer.invoke("speech", SSML);
67+
return result; // 执行成功,返回结果
68+
} catch (error) {
69+
console.error("Speech invocation failed:", error);
70+
await sleep(delay); // 暂停一段时间后再重试
71+
}
72+
retry++;
73+
}
74+
throw new Error(`Speech invocation failed after ${retryCount} retries`); // 重试次数用尽,抛出异常
75+
}
76+
function sleep(ms: number) {
77+
return new Promise(resolve => setTimeout(resolve, ms));
78+
}
79+
5980
export default getTTSData;

src/store/store.ts

+33-16
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,8 @@ export const useTtsStore = defineStore("ttsStore", {
3939
speechKey: store.get("speechKey"),
4040
serviceRegion: store.get("serviceRegion"),
4141
disclaimers: store.get("disclaimers"),
42+
retryCount: store.get("retryCount"),
43+
retryInterval: store.get("retryInterval"),
4244
},
4345
isLoading: false,
4446
currMp3Buffer: Buffer.alloc(0),
@@ -95,10 +97,16 @@ export const useTtsStore = defineStore("ttsStore", {
9597
store.set("autoplay", this.config.autoplay);
9698
},
9799
setSpeechKey() {
98-
store.set("speechKey", this.config.speechKey);
100+
store.set("speechKey", this.config.speechKey);
99101
},
100102
setServiceRegion() {
101-
store.set("serviceRegion", this.config.serviceRegion);
103+
store.set("serviceRegion", this.config.serviceRegion);
104+
},
105+
setRetryCount() {
106+
store.set("retryCount", parseInt(this.config.retryCount));
107+
},
108+
setRetryInterval() {
109+
store.set("retryInterval", parseInt(this.config.retryInterval));
102110
},
103111
addFormConfig() {
104112
this.config.formConfigJson[this.currConfigName] = this.formConfig;
@@ -134,8 +142,12 @@ export const useTtsStore = defineStore("ttsStore", {
134142
? this.inputs.inputValue
135143
: this.inputs.ssmlValue,
136144
};
137-
if (this.page.tabIndex == "1" && this.formConfig.api == 1 && this.inputs.inputValue.length > 400) {
138-
const delimiters = ",。?,.?".split("");
145+
if (
146+
this.page.tabIndex == "1" &&
147+
this.formConfig.api == 1 &&
148+
this.inputs.inputValue.length > 400
149+
) {
150+
const delimiters = [",", "。", "?", ",", ".", "?", "\n"];
139151
const maxSize = 300;
140152
ipcRenderer.send("log.info", "字数过多,正在对文本切片。。。");
141153

@@ -177,7 +189,8 @@ export const useTtsStore = defineStore("ttsStore", {
177189
(this.formConfig.pitch - 1) * 50,
178190
this.formConfig.api,
179191
this.config.speechKey,
180-
this.config.serviceRegion
192+
this.config.serviceRegion,
193+
this.config.retryCount,
181194
);
182195
this.currMp3Buffer = Buffer.concat([this.currMp3Buffer, buffers]);
183196
ipcRenderer.send(
@@ -220,7 +233,8 @@ export const useTtsStore = defineStore("ttsStore", {
220233
(this.formConfig.pitch - 1) * 50,
221234
this.formConfig.api,
222235
this.config.speechKey,
223-
this.config.serviceRegion
236+
this.config.serviceRegion,
237+
this.config.retryCount,
224238
)
225239
.then((mp3buffer: any) => {
226240
this.currMp3Buffer = mp3buffer;
@@ -318,7 +332,8 @@ export const useTtsStore = defineStore("ttsStore", {
318332
(this.formConfig.pitch - 1) * 50,
319333
this.formConfig.api,
320334
this.config.speechKey,
321-
this.config.serviceRegion
335+
this.config.serviceRegion,
336+
this.config.retryCount,
322337
);
323338
buffer = Buffer.concat([buffer, buffers]);
324339
ipcRenderer.send(
@@ -365,7 +380,8 @@ export const useTtsStore = defineStore("ttsStore", {
365380
(this.formConfig.pitch - 1) * 50,
366381
this.formConfig.api,
367382
this.config.speechKey,
368-
this.config.serviceRegion
383+
this.config.serviceRegion,
384+
this.config.retryCount,
369385
)
370386
.then((mp3buffer: any) => {
371387
fs.writeFileSync(filePath, mp3buffer);
@@ -430,7 +446,8 @@ export const useTtsStore = defineStore("ttsStore", {
430446
(this.formConfig.pitch - 1) * 50,
431447
this.formConfig.api,
432448
this.config.speechKey,
433-
this.config.serviceRegion
449+
this.config.serviceRegion,
450+
this.config.retryCount,
434451
)
435452
.then((mp3buffer: any) => {
436453
this.currMp3Buffer = mp3buffer;
@@ -448,16 +465,16 @@ export const useTtsStore = defineStore("ttsStore", {
448465
showDisclaimers() {
449466
if (!this.config.disclaimers) {
450467
ElMessageBox.confirm(
451-
'该软件以及代码仅为个人学习测试使用,请在下载后24小时内删除,不得用于商业用途,否则后果自负。任何违规使用造成的法律后果与本人无关。该软件也永远不会收费,如果您使用该软件前支付了额外费用,或付费获得源码以及成品软件,那么你一定被骗了!',
452-
'注意!',
468+
"该软件以及代码仅为个人学习测试使用,请在下载后24小时内删除,不得用于商业用途,否则后果自负。任何违规使用造成的法律后果与本人无关。该软件也永远不会收费,如果您使用该软件前支付了额外费用,或付费获得源码以及成品软件,那么你一定被骗了!",
469+
"注意!",
453470
{
454-
confirmButtonText: '我已确认,不再弹出',
455-
cancelButtonText: '取消',
456-
type: 'warning',
471+
confirmButtonText: "我已确认,不再弹出",
472+
cancelButtonText: "取消",
473+
type: "warning"
457474
}
458475
).then(() => {
459-
store.set('disclaimers', true)
460-
})
476+
store.set("disclaimers", true);
477+
});
461478
}
462479
}
463480
},

0 commit comments

Comments
 (0)