ssml-builder-js 2.8.0 → 2.8.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +16 -10
- package/dist/{chunk-4RQETJUI.mjs → chunk-MWSDFGXW.mjs} +156 -3
- package/dist/chunk-MWSDFGXW.mjs.map +1 -0
- package/dist/{chunk-TKD3PU5Y.mjs → chunk-VCDMKVVT.mjs} +155 -101
- package/dist/chunk-VCDMKVVT.mjs.map +1 -0
- package/dist/core.d.mts +8 -2
- package/dist/core.d.ts +8 -2
- package/dist/core.js +155 -100
- package/dist/core.js.map +1 -1
- package/dist/core.mjs +3 -1
- package/dist/elements.js +175 -3
- package/dist/elements.js.map +1 -1
- package/dist/elements.mjs +25 -2
- package/dist/elements.mjs.map +1 -1
- package/dist/index.d.mts +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +155 -100
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +3 -1
- package/dist/index.mjs.map +1 -1
- package/dist/react.d.mts +8 -4
- package/dist/react.d.ts +8 -4
- package/dist/react.js +194 -7
- package/dist/react.js.map +1 -1
- package/dist/react.mjs +44 -6
- package/dist/react.mjs.map +1 -1
- package/package.json +3 -2
- package/dist/chunk-4RQETJUI.mjs.map +0 -1
- package/dist/chunk-TKD3PU5Y.mjs.map +0 -1
package/dist/core.d.ts
CHANGED
|
@@ -99,11 +99,15 @@ interface MsttsVisemeElement extends SsmlElementBase {
|
|
|
99
99
|
typeValue?: string;
|
|
100
100
|
visemeType?: string;
|
|
101
101
|
}
|
|
102
|
+
interface MsttsAudioDurationElement extends SsmlElementBase {
|
|
103
|
+
type: "mstts:audioduration";
|
|
104
|
+
value?: SsmlAttributeValue;
|
|
105
|
+
}
|
|
102
106
|
interface CustomElement extends SsmlElementBase {
|
|
103
107
|
type: "custom" | "element";
|
|
104
108
|
name: string;
|
|
105
109
|
}
|
|
106
|
-
type SsmlElement = VoiceElement | ProsodyElement | BreakElement | ExpressAsElement | SayAsElement | PhonemeElement | EmphasisElement | AudioElement | SubElement | LangElement | MarkElement | BookmarkElement | LexiconElement | ParagraphElement | SentenceElement | WordElement | MsttsSilenceElement | MsttsVisemeElement | CustomElement;
|
|
110
|
+
type SsmlElement = VoiceElement | ProsodyElement | BreakElement | ExpressAsElement | SayAsElement | PhonemeElement | EmphasisElement | AudioElement | SubElement | LangElement | MarkElement | BookmarkElement | LexiconElement | ParagraphElement | SentenceElement | WordElement | MsttsSilenceElement | MsttsVisemeElement | MsttsAudioDurationElement | CustomElement;
|
|
107
111
|
interface SsmlDocument {
|
|
108
112
|
type?: "speak";
|
|
109
113
|
version: string;
|
|
@@ -209,10 +213,12 @@ interface AzureValidationOptions {
|
|
|
209
213
|
type AzureLanguageNormalizationOptions = Pick<AzureValidationOptions, "languageAliases" | "normalizeLanguage">;
|
|
210
214
|
/** @deprecated Use AzureValidationOptions instead. */
|
|
211
215
|
type AzureSsmlValidationOptions = AzureValidationOptions;
|
|
216
|
+
/** Returns whether a value is a positive Azure SSML audio duration. */
|
|
217
|
+
declare function isValidAzureAudioDuration(value: string): boolean;
|
|
212
218
|
/** Normalizes an Azure language tag using BCP 47 and the configured aliases. */
|
|
213
219
|
declare function normalizeAzureLanguage(language: string, options?: AzureLanguageNormalizationOptions): string;
|
|
214
220
|
/** Compares two Azure language tags after BCP 47 and alias normalization. */
|
|
215
221
|
declare function areAzureLanguagesEquivalent(first: string, second: string, options?: AzureLanguageNormalizationOptions): boolean;
|
|
216
222
|
declare function validateAzureSsml(ssml: string, options?: AzureValidationOptions): SsmlDiagnostic[];
|
|
217
223
|
|
|
218
|
-
export { type AudioElement, type AzureDiagnosticCode, type AzureLanguageNormalizationOptions, type AzureSsmlValidationOptions, type AzureValidationOptions, type AzureVoiceDefinition, type AzureVoiceMetadata, type BookmarkElement, type BreakElement, type BuildPartialSsmlOptions, type CustomElement, type EmphasisElement, type ExpressAsElement, type LangElement, type LexiconElement, type MapSsmlTextNodesOptions, type MarkElement, type MsttsSilenceElement, type MsttsVisemeElement, type NamedElement, type ParagraphElement, type PhonemeElement, type ProsodyElement, type SayAsElement, type SentenceElement, type SsmlAttributeValue, type SsmlAttributes, type SsmlBreakElement, type SsmlDiagnostic, type SsmlDiagnosticSeverity, type SsmlDiagnosticSource, type SsmlDocument, type SsmlElement, type SsmlElementBase, type SsmlExpressAsElement, type SsmlNode, type SsmlPartialContext, type SsmlPartialProsody, type SsmlPartialVoice, type SsmlPhonemeElement, type SsmlProsodyElement, type SsmlSayAsElement, type SsmlText, type SsmlTextNodeContext, type SsmlValidationError, type SsmlVoiceElement, type SubElement, type VoiceElement, type WordElement, areAzureLanguagesEquivalent, buildPartialSsml, buildSsml, extractSsmlText, mapSsmlTextNodes, normalizeAzureLanguage, parseSsml, validateAzureSsml, validateSsml };
|
|
224
|
+
export { type AudioElement, type AzureDiagnosticCode, type AzureLanguageNormalizationOptions, type AzureSsmlValidationOptions, type AzureValidationOptions, type AzureVoiceDefinition, type AzureVoiceMetadata, type BookmarkElement, type BreakElement, type BuildPartialSsmlOptions, type CustomElement, type EmphasisElement, type ExpressAsElement, type LangElement, type LexiconElement, type MapSsmlTextNodesOptions, type MarkElement, type MsttsAudioDurationElement, type MsttsSilenceElement, type MsttsVisemeElement, type NamedElement, type ParagraphElement, type PhonemeElement, type ProsodyElement, type SayAsElement, type SentenceElement, type SsmlAttributeValue, type SsmlAttributes, type SsmlBreakElement, type SsmlDiagnostic, type SsmlDiagnosticSeverity, type SsmlDiagnosticSource, type SsmlDocument, type SsmlElement, type SsmlElementBase, type SsmlExpressAsElement, type SsmlNode, type SsmlPartialContext, type SsmlPartialProsody, type SsmlPartialVoice, type SsmlPhonemeElement, type SsmlProsodyElement, type SsmlSayAsElement, type SsmlText, type SsmlTextNodeContext, type SsmlValidationError, type SsmlVoiceElement, type SubElement, type VoiceElement, type WordElement, areAzureLanguagesEquivalent, buildPartialSsml, buildSsml, extractSsmlText, isValidAzureAudioDuration, mapSsmlTextNodes, normalizeAzureLanguage, parseSsml, validateAzureSsml, validateSsml };
|
package/dist/core.js
CHANGED
|
@@ -31,6 +31,7 @@ __export(core_exports, {
|
|
|
31
31
|
buildPartialSsml: () => buildPartialSsml,
|
|
32
32
|
buildSsml: () => buildSsml,
|
|
33
33
|
extractSsmlText: () => extractSsmlText,
|
|
34
|
+
isValidAzureAudioDuration: () => isValidAzureAudioDuration,
|
|
34
35
|
mapSsmlTextNodes: () => mapSsmlTextNodes,
|
|
35
36
|
normalizeAzureLanguage: () => normalizeAzureLanguage,
|
|
36
37
|
parseSsml: () => parseSsml,
|
|
@@ -71,7 +72,8 @@ var SSML_TAGS = {
|
|
|
71
72
|
MSTTS_SILENCE: "mstts:silence",
|
|
72
73
|
SILENCE: "silence",
|
|
73
74
|
MSTTS_VISEME: "mstts:viseme",
|
|
74
|
-
VISEME: "viseme"
|
|
75
|
+
VISEME: "viseme",
|
|
76
|
+
MSTTS_AUDIO_DURATION: "mstts:audioduration"
|
|
75
77
|
};
|
|
76
78
|
var SSML_ATTRS = {
|
|
77
79
|
VERSION: "version",
|
|
@@ -200,6 +202,9 @@ function getAttributes(element) {
|
|
|
200
202
|
case SSML_TAGS.VISEME:
|
|
201
203
|
addAttribute(attributes, SSML_ATTRS.TYPE, element.typeValue ?? element.visemeType);
|
|
202
204
|
break;
|
|
205
|
+
case SSML_TAGS.MSTTS_AUDIO_DURATION:
|
|
206
|
+
addAttribute(attributes, SSML_ATTRS.VALUE, element.value);
|
|
207
|
+
break;
|
|
203
208
|
case SSML_TAGS.PARAGRAPH:
|
|
204
209
|
case SSML_TAGS.SENTENCE:
|
|
205
210
|
case SSML_TAGS.WORD:
|
|
@@ -224,6 +229,8 @@ function getTagName(element) {
|
|
|
224
229
|
case SSML_TAGS.VISEME:
|
|
225
230
|
case SSML_TAGS.MSTTS_VISEME:
|
|
226
231
|
return SSML_TAGS.MSTTS_VISEME;
|
|
232
|
+
case SSML_TAGS.MSTTS_AUDIO_DURATION:
|
|
233
|
+
return SSML_TAGS.MSTTS_AUDIO_DURATION;
|
|
227
234
|
case "element":
|
|
228
235
|
case "custom":
|
|
229
236
|
return element.name;
|
|
@@ -758,6 +765,12 @@ function convertElement(node) {
|
|
|
758
765
|
if (typeValue !== void 0) element.typeValue = typeValue;
|
|
759
766
|
return finishElement(element, node, attributes);
|
|
760
767
|
}
|
|
768
|
+
case SSML_TAGS.MSTTS_AUDIO_DURATION: {
|
|
769
|
+
const element = { type: SSML_TAGS.MSTTS_AUDIO_DURATION };
|
|
770
|
+
const value = readAttribute(attributes, SSML_ATTRS.VALUE);
|
|
771
|
+
if (value !== void 0) element.value = value;
|
|
772
|
+
return finishElement(element, node, attributes);
|
|
773
|
+
}
|
|
761
774
|
default: {
|
|
762
775
|
const element = {
|
|
763
776
|
name: node.name,
|
|
@@ -1032,93 +1045,126 @@ async function mapSsmlTextNodes(ssml, transform, options = {}) {
|
|
|
1032
1045
|
return result + ssml.slice(cursor);
|
|
1033
1046
|
}
|
|
1034
1047
|
|
|
1048
|
+
// packages/ssml-core/src/generated/azureVoiceDefinitions.ts
|
|
1049
|
+
var AZURE_VOICE_DEFINITIONS = [
|
|
1050
|
+
{ name: "de-DE-ConradNeural", locale: "de-DE", styles: ["cheerful", "sad"] },
|
|
1051
|
+
{ name: "de-DE-KatjaNeural", locale: "de-DE", styles: ["cheerful", "sad"] },
|
|
1052
|
+
{ name: "en-US-AndrewNeural", locale: "en-US", styles: ["empathetic", "relieved"] },
|
|
1053
|
+
{
|
|
1054
|
+
name: "en-US-GuyNeural",
|
|
1055
|
+
locale: "en-US",
|
|
1056
|
+
styles: [
|
|
1057
|
+
"angry",
|
|
1058
|
+
"cheerful",
|
|
1059
|
+
"excited",
|
|
1060
|
+
"friendly",
|
|
1061
|
+
"hopeful",
|
|
1062
|
+
"newscast",
|
|
1063
|
+
"sad",
|
|
1064
|
+
"shouting",
|
|
1065
|
+
"terrified",
|
|
1066
|
+
"unfriendly",
|
|
1067
|
+
"whispering"
|
|
1068
|
+
]
|
|
1069
|
+
},
|
|
1070
|
+
{
|
|
1071
|
+
name: "en-US-JennyMultilingualNeural",
|
|
1072
|
+
locale: "en-US",
|
|
1073
|
+
styles: [
|
|
1074
|
+
"cheerful",
|
|
1075
|
+
"empathetic",
|
|
1076
|
+
"excited",
|
|
1077
|
+
"friendly",
|
|
1078
|
+
"hopeful",
|
|
1079
|
+
"sad",
|
|
1080
|
+
"shouting",
|
|
1081
|
+
"terrified",
|
|
1082
|
+
"unfriendly",
|
|
1083
|
+
"whispering"
|
|
1084
|
+
]
|
|
1085
|
+
},
|
|
1086
|
+
{
|
|
1087
|
+
name: "en-US-JennyNeural",
|
|
1088
|
+
locale: "en-US",
|
|
1089
|
+
styles: [
|
|
1090
|
+
"assistant",
|
|
1091
|
+
"chat",
|
|
1092
|
+
"customerservice",
|
|
1093
|
+
"newscast",
|
|
1094
|
+
"cheerful",
|
|
1095
|
+
"empathetic",
|
|
1096
|
+
"excited",
|
|
1097
|
+
"friendly",
|
|
1098
|
+
"hopeful",
|
|
1099
|
+
"sad",
|
|
1100
|
+
"shouting",
|
|
1101
|
+
"terrified",
|
|
1102
|
+
"unfriendly",
|
|
1103
|
+
"whispering"
|
|
1104
|
+
]
|
|
1105
|
+
},
|
|
1106
|
+
{ name: "es-ES-ElviraNeural", locale: "es-ES" },
|
|
1107
|
+
{ name: "fil-PH-AngeloNeural", locale: "fil-PH" },
|
|
1108
|
+
{ name: "fr-FR-DeniseNeural", locale: "fr-FR", styles: ["cheerful", "sad"] },
|
|
1109
|
+
{ name: "fr-FR-HenriNeural", locale: "fr-FR", styles: ["cheerful", "sad"] },
|
|
1110
|
+
{ name: "id-ID-GadisNeural", locale: "id-ID" },
|
|
1111
|
+
{ name: "it-IT-ElsaNeural", locale: "it-IT", styles: ["cheerful", "sad"] },
|
|
1112
|
+
{ name: "ja-JP-KeitaNeural", locale: "ja-JP", styles: ["chat"] },
|
|
1113
|
+
{ name: "ja-JP-MayuNeural", locale: "ja-JP", styles: ["calm", "cheerful", "sad"] },
|
|
1114
|
+
{ name: "ja-JP-NanamiNeural", locale: "ja-JP", styles: ["chat", "customerservice", "cheerful", "whispering", "sad"] },
|
|
1115
|
+
{ name: "ko-KR-SunHiNeural", locale: "ko-KR", styles: ["cheerful", "sad"] },
|
|
1116
|
+
{ name: "ms-MY-YasminNeural", locale: "ms-MY" },
|
|
1117
|
+
{ name: "pt-BR-FranciscaNeural", locale: "pt-BR", styles: ["calm"] },
|
|
1118
|
+
{
|
|
1119
|
+
name: "ru-RU-SvetlanaNeural",
|
|
1120
|
+
locale: "ru-RU",
|
|
1121
|
+
styles: ["cheerful", "sad", "angry", "disgruntled", "embarrassed", "fearful"]
|
|
1122
|
+
},
|
|
1123
|
+
{ name: "th-TH-PremwadeeNeural", locale: "th-TH" },
|
|
1124
|
+
{ name: "vi-VN-HoaiMyNeural", locale: "vi-VN" },
|
|
1125
|
+
{
|
|
1126
|
+
name: "zh-CN-XiaoxiaoNeural",
|
|
1127
|
+
locale: "zh-CN",
|
|
1128
|
+
styles: [
|
|
1129
|
+
"assistant",
|
|
1130
|
+
"chat",
|
|
1131
|
+
"customerservice",
|
|
1132
|
+
"newscast",
|
|
1133
|
+
"cheerful",
|
|
1134
|
+
"empathetic",
|
|
1135
|
+
"excited",
|
|
1136
|
+
"friendly",
|
|
1137
|
+
"hopeful",
|
|
1138
|
+
"sad",
|
|
1139
|
+
"terrified",
|
|
1140
|
+
"whispering",
|
|
1141
|
+
"poetry-reading",
|
|
1142
|
+
"sports_commentary",
|
|
1143
|
+
"sports_commentary_excited",
|
|
1144
|
+
"story"
|
|
1145
|
+
]
|
|
1146
|
+
},
|
|
1147
|
+
{
|
|
1148
|
+
name: "zh-CN-YunxiNeural",
|
|
1149
|
+
locale: "zh-CN",
|
|
1150
|
+
styles: [
|
|
1151
|
+
"narration-relaxed",
|
|
1152
|
+
"embarrassed",
|
|
1153
|
+
"fearful",
|
|
1154
|
+
"sad",
|
|
1155
|
+
"disgruntled",
|
|
1156
|
+
"serious",
|
|
1157
|
+
"angry",
|
|
1158
|
+
"depressed",
|
|
1159
|
+
"chat",
|
|
1160
|
+
"cheerful",
|
|
1161
|
+
"assistant"
|
|
1162
|
+
]
|
|
1163
|
+
},
|
|
1164
|
+
{ name: "zh-TW-HsiaoChenNeural", locale: "zh-TW" }
|
|
1165
|
+
];
|
|
1166
|
+
|
|
1035
1167
|
// packages/ssml-core/src/azureValidation.ts
|
|
1036
|
-
var EXPRESS_AS_STYLES = {
|
|
1037
|
-
"en-us-jennyneural": [
|
|
1038
|
-
"assistant",
|
|
1039
|
-
"chat",
|
|
1040
|
-
"customerservice",
|
|
1041
|
-
"newscast",
|
|
1042
|
-
"cheerful",
|
|
1043
|
-
"empathetic",
|
|
1044
|
-
"excited",
|
|
1045
|
-
"friendly",
|
|
1046
|
-
"hopeful",
|
|
1047
|
-
"sad",
|
|
1048
|
-
"shouting",
|
|
1049
|
-
"terrified",
|
|
1050
|
-
"unfriendly",
|
|
1051
|
-
"whispering"
|
|
1052
|
-
],
|
|
1053
|
-
"en-us-guyneural": [
|
|
1054
|
-
"angry",
|
|
1055
|
-
"cheerful",
|
|
1056
|
-
"excited",
|
|
1057
|
-
"friendly",
|
|
1058
|
-
"hopeful",
|
|
1059
|
-
"newscast",
|
|
1060
|
-
"sad",
|
|
1061
|
-
"shouting",
|
|
1062
|
-
"terrified",
|
|
1063
|
-
"unfriendly",
|
|
1064
|
-
"whispering"
|
|
1065
|
-
],
|
|
1066
|
-
"en-us-jennymultilingualneural": [
|
|
1067
|
-
"cheerful",
|
|
1068
|
-
"empathetic",
|
|
1069
|
-
"excited",
|
|
1070
|
-
"friendly",
|
|
1071
|
-
"hopeful",
|
|
1072
|
-
"sad",
|
|
1073
|
-
"shouting",
|
|
1074
|
-
"terrified",
|
|
1075
|
-
"unfriendly",
|
|
1076
|
-
"whispering"
|
|
1077
|
-
],
|
|
1078
|
-
"en-us-andrewneural": ["empathetic", "relieved"],
|
|
1079
|
-
"ja-jp-mayuneural": ["calm", "cheerful", "sad"],
|
|
1080
|
-
"ja-jp-nanamineural": ["chat", "customerservice", "cheerful", "whispering", "sad"],
|
|
1081
|
-
"ja-jp-keitaneural": ["chat"],
|
|
1082
|
-
"ko-kr-sunhineural": ["cheerful", "sad"],
|
|
1083
|
-
"zh-cn-yunxineural": [
|
|
1084
|
-
"narration-relaxed",
|
|
1085
|
-
"embarrassed",
|
|
1086
|
-
"fearful",
|
|
1087
|
-
"sad",
|
|
1088
|
-
"disgruntled",
|
|
1089
|
-
"serious",
|
|
1090
|
-
"angry",
|
|
1091
|
-
"depressed",
|
|
1092
|
-
"chat",
|
|
1093
|
-
"cheerful",
|
|
1094
|
-
"assistant"
|
|
1095
|
-
],
|
|
1096
|
-
"zh-cn-xiaoxiaoneural": [
|
|
1097
|
-
"assistant",
|
|
1098
|
-
"chat",
|
|
1099
|
-
"customerservice",
|
|
1100
|
-
"newscast",
|
|
1101
|
-
"cheerful",
|
|
1102
|
-
"empathetic",
|
|
1103
|
-
"excited",
|
|
1104
|
-
"friendly",
|
|
1105
|
-
"hopeful",
|
|
1106
|
-
"sad",
|
|
1107
|
-
"terrified",
|
|
1108
|
-
"whispering",
|
|
1109
|
-
"poetry-reading",
|
|
1110
|
-
"sports_commentary",
|
|
1111
|
-
"sports_commentary_excited",
|
|
1112
|
-
"story"
|
|
1113
|
-
],
|
|
1114
|
-
"fr-fr-deniseneural": ["cheerful", "sad"],
|
|
1115
|
-
"fr-fr-henrineural": ["cheerful", "sad"],
|
|
1116
|
-
"pt-br-franciscaneural": ["calm"],
|
|
1117
|
-
"it-it-elsaneural": ["cheerful", "sad"],
|
|
1118
|
-
"de-de-katjaneural": ["cheerful", "sad"],
|
|
1119
|
-
"de-de-conradneural": ["cheerful", "sad"],
|
|
1120
|
-
"ru-ru-svetlananeural": ["cheerful", "sad", "angry", "disgruntled", "embarrassed", "fearful"]
|
|
1121
|
-
};
|
|
1122
1168
|
var ALLOWED_BREAK_STRENGTHS = /* @__PURE__ */ new Set(["none", "x-weak", "weak", "medium", "strong", "x-strong"]);
|
|
1123
1169
|
var ALLOWED_SAY_AS = /* @__PURE__ */ new Set([
|
|
1124
1170
|
"characters",
|
|
@@ -1247,18 +1293,17 @@ function isSupportedProsodyRate(value) {
|
|
|
1247
1293
|
const numericValue = Number(multiplier[1]);
|
|
1248
1294
|
return numericValue >= 0.5 && numericValue <= 2;
|
|
1249
1295
|
}
|
|
1296
|
+
function isValidAzureAudioDuration(value) {
|
|
1297
|
+
const trimmed = value.trim();
|
|
1298
|
+
const numeric = /^(\d+(?:\.\d+)?)(ms|s)$/.exec(trimmed);
|
|
1299
|
+
if (numeric) return Number(numeric[1]) > 0;
|
|
1300
|
+
const clock = /^(\d{2,}):([0-5]\d):([0-5]\d)(?:\.(\d{1,3}))?$/.exec(trimmed);
|
|
1301
|
+
if (!clock) return false;
|
|
1302
|
+
return Number(clock[1]) > 0 || Number(clock[2]) > 0 || Number(clock[3]) > 0 || Number(clock[4] ?? 0) > 0;
|
|
1303
|
+
}
|
|
1250
1304
|
function attr(token, name) {
|
|
1251
1305
|
return token.attributes.get(name.toLowerCase());
|
|
1252
1306
|
}
|
|
1253
|
-
var ADDITIONAL_VOICE_DEFINITIONS = [
|
|
1254
|
-
{ name: "zh-TW-HsiaoChenNeural", locale: "zh-TW" },
|
|
1255
|
-
{ name: "es-ES-ElviraNeural", locale: "es-ES" },
|
|
1256
|
-
{ name: "th-TH-PremwadeeNeural", locale: "th-TH" },
|
|
1257
|
-
{ name: "fil-PH-AngeloNeural", locale: "fil-PH" },
|
|
1258
|
-
{ name: "vi-VN-HoaiMyNeural", locale: "vi-VN" },
|
|
1259
|
-
{ name: "id-ID-GadisNeural", locale: "id-ID" },
|
|
1260
|
-
{ name: "ms-MY-YasminNeural", locale: "ms-MY" }
|
|
1261
|
-
];
|
|
1262
1307
|
var DEFAULT_LANGUAGE_ALIASES = {
|
|
1263
1308
|
"zh-CN": ["zh-Hans"],
|
|
1264
1309
|
"zh-TW": ["zh-Hant"]
|
|
@@ -1321,10 +1366,7 @@ function definitionFromStyleMap(voiceName, styles) {
|
|
|
1321
1366
|
}
|
|
1322
1367
|
function normalizeVoiceCatalog(options) {
|
|
1323
1368
|
const definitions = /* @__PURE__ */ new Map();
|
|
1324
|
-
for (const
|
|
1325
|
-
definitions.set(name.toLowerCase(), definitionFromStyleMap(name, styles));
|
|
1326
|
-
}
|
|
1327
|
-
for (const definition of ADDITIONAL_VOICE_DEFINITIONS) definitions.set(definition.name.toLowerCase(), definition);
|
|
1369
|
+
for (const definition of AZURE_VOICE_DEFINITIONS) definitions.set(definition.name.toLowerCase(), definition);
|
|
1328
1370
|
for (const definition of options.voiceCatalog ?? []) definitions.set(definition.name.toLowerCase(), definition);
|
|
1329
1371
|
for (const definition of options.voiceDefinitions ?? []) definitions.set(definition.name.toLowerCase(), definition);
|
|
1330
1372
|
for (const definition of options.customVoiceDefinitions ?? [])
|
|
@@ -1461,6 +1503,18 @@ function validateElement(token, source, diagnostics, voiceName, options, voiceCa
|
|
|
1461
1503
|
if (!value || !/^\d+(?:\.\d+)?(?:ms|s)$/.test(value.trim()))
|
|
1462
1504
|
addDiagnostic(diagnostics, source, token.start, '<mstts:silence> requires a time-valued "value" attribute.');
|
|
1463
1505
|
}
|
|
1506
|
+
if (name === "mstts:audioduration") {
|
|
1507
|
+
const value = attr(token, "value");
|
|
1508
|
+
if (!value || !isValidAzureAudioDuration(value))
|
|
1509
|
+
addDiagnostic(
|
|
1510
|
+
diagnostics,
|
|
1511
|
+
source,
|
|
1512
|
+
token.start,
|
|
1513
|
+
'<mstts:audioduration> requires a positive duration such as "10s", "5000ms", or "00:00:10".'
|
|
1514
|
+
);
|
|
1515
|
+
if (!token.selfClosing)
|
|
1516
|
+
addDiagnostic(diagnostics, source, token.start, "<mstts:audioduration> must be self-closing.");
|
|
1517
|
+
}
|
|
1464
1518
|
if (name === "mstts:viseme") {
|
|
1465
1519
|
const type = attr(token, "type");
|
|
1466
1520
|
if (!type || !ALLOWED_VISEME_TYPES.has(type))
|
|
@@ -1566,6 +1620,7 @@ function validateAzureSsml(ssml, options = {}) {
|
|
|
1566
1620
|
buildPartialSsml,
|
|
1567
1621
|
buildSsml,
|
|
1568
1622
|
extractSsmlText,
|
|
1623
|
+
isValidAzureAudioDuration,
|
|
1569
1624
|
mapSsmlTextNodes,
|
|
1570
1625
|
normalizeAzureLanguage,
|
|
1571
1626
|
parseSsml,
|