@streamoji/aitwin 0.3.8 → 0.4.0
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/dist/aitwin.cjs +3 -3
- package/dist/aitwin.js +1517 -1527
- package/package.json +1 -1
package/dist/aitwin.js
CHANGED
|
@@ -1,47 +1,47 @@
|
|
|
1
|
-
import { jsxs as
|
|
2
|
-
import { forwardRef as
|
|
1
|
+
import { jsxs as _r, jsx as yn } from "react/jsx-runtime";
|
|
2
|
+
import { forwardRef as Sr, useRef as L, useState as ct, useEffect as Le, useCallback as Se, useMemo as _n, useImperativeHandle as vr } from "react";
|
|
3
3
|
import { PipecatClient as kr } from "@pipecat-ai/client-js";
|
|
4
|
-
import { WebSocketTransport as
|
|
5
|
-
const
|
|
6
|
-
publicBase:
|
|
7
|
-
},
|
|
8
|
-
version:
|
|
9
|
-
}, Mr = {},
|
|
4
|
+
import { WebSocketTransport as br, DailyMediaManager as Er, ProtobufFrameSerializer as Tr } from "@pipecat-ai/websocket-transport";
|
|
5
|
+
const Ar = "https://aitwin.bubu.social", Hn = {
|
|
6
|
+
publicBase: Ar
|
|
7
|
+
}, Ir = "0.4.0", Pr = {
|
|
8
|
+
version: Ir
|
|
9
|
+
}, Mr = {}, dt = "https://ai.aitwin.me", zt = `${Hn.publicBase}/custom-faces`, Dr = `${Hn.publicBase}/aitwin-workers/v${Pr.version}/visemeDiffPreview.worker.js`;
|
|
10
10
|
function Rr(e) {
|
|
11
11
|
if (e) return e;
|
|
12
12
|
const t = typeof import.meta < "u" ? Mr?.VITE_AITWIN_WORKER_URL : void 0;
|
|
13
|
-
return t?.trim() ? t.trim() :
|
|
13
|
+
return t?.trim() ? t.trim() : Dr;
|
|
14
14
|
}
|
|
15
|
-
const
|
|
15
|
+
const Br = "https://us-central1-streamoji-265f4.cloudfunctions.net/getAiTwin", Ft = 3e3, ft = 16, Sn = 3e3, Cr = 4e3, xr = 0.85, Fr = 8, Yt = 400, $n = "eng_a7f2b9c1", Jt = "eng_d4e8f3a2", Ze = "eng_c9b1e6d4", Ye = Ze, qn = /* @__PURE__ */ new Set([
|
|
16
16
|
Jt,
|
|
17
|
-
|
|
18
|
-
]),
|
|
19
|
-
[
|
|
20
|
-
[
|
|
17
|
+
Ze
|
|
18
|
+
]), Kn = {
|
|
19
|
+
[$n]: "oculus_direct",
|
|
20
|
+
[Ze]: "oculus_direct",
|
|
21
21
|
[Jt]: "inworld_word"
|
|
22
|
-
},
|
|
23
|
-
google:
|
|
22
|
+
}, vn = {
|
|
23
|
+
google: $n,
|
|
24
24
|
inworld: Jt,
|
|
25
|
-
cartesia:
|
|
25
|
+
cartesia: Ze
|
|
26
26
|
};
|
|
27
|
-
function
|
|
28
|
-
return
|
|
27
|
+
function Lr(e) {
|
|
28
|
+
return Kn[e];
|
|
29
29
|
}
|
|
30
|
-
function
|
|
31
|
-
return e ===
|
|
30
|
+
function Nr(e) {
|
|
31
|
+
return e === Ze;
|
|
32
32
|
}
|
|
33
|
-
function
|
|
34
|
-
if (e.ttsEngineId && e.ttsEngineId in
|
|
33
|
+
function Or(e) {
|
|
34
|
+
if (e.ttsEngineId && e.ttsEngineId in Kn)
|
|
35
35
|
return e.ttsEngineId;
|
|
36
36
|
const t = e.tts?.toLowerCase();
|
|
37
|
-
return t && t in
|
|
37
|
+
return t && t in vn ? vn[t] : Ye;
|
|
38
38
|
}
|
|
39
39
|
class Vt extends Error {
|
|
40
40
|
constructor(t = "AI twin not found") {
|
|
41
41
|
super(t), this.name = "AiTwinNotFoundError";
|
|
42
42
|
}
|
|
43
43
|
}
|
|
44
|
-
async function
|
|
44
|
+
async function Ur(e, t = Br) {
|
|
45
45
|
const n = new URL(t);
|
|
46
46
|
n.searchParams.set("id", e);
|
|
47
47
|
const r = await fetch(n.toString());
|
|
@@ -55,22 +55,22 @@ async function Nr(e, t = Dr) {
|
|
|
55
55
|
const { tts: i, token: a, ...o } = s.data, d = String(o.authToken ?? a ?? "").trim() || void 0;
|
|
56
56
|
return {
|
|
57
57
|
...o,
|
|
58
|
-
ttsEngineId:
|
|
58
|
+
ttsEngineId: Or(s.data),
|
|
59
59
|
authToken: d
|
|
60
60
|
};
|
|
61
61
|
}
|
|
62
|
-
const
|
|
63
|
-
async function
|
|
64
|
-
const e = await fetch(
|
|
62
|
+
const Vr = "https://us-central1-streamoji-265f4.cloudfunctions.net/getAuthToken", Wr = "client_6TNvp3SCs4Og0a1ijm9TommXLql1", Hr = "kk8Fq8EmexzP10jMIEwY3R44M5RKUEm1", $r = "6TNvp3SCs4Og0a1ijm9TommXLql1", qr = "Swaraj Mali";
|
|
63
|
+
async function Lt() {
|
|
64
|
+
const e = await fetch(Vr, {
|
|
65
65
|
method: "POST",
|
|
66
66
|
headers: {
|
|
67
67
|
"Content-Type": "application/json",
|
|
68
|
-
"Client-Id":
|
|
69
|
-
"Client-Secret":
|
|
68
|
+
"Client-Id": Wr,
|
|
69
|
+
"Client-Secret": Hr
|
|
70
70
|
},
|
|
71
71
|
body: JSON.stringify({
|
|
72
|
-
userId:
|
|
73
|
-
userName:
|
|
72
|
+
userId: $r,
|
|
73
|
+
userName: qr
|
|
74
74
|
})
|
|
75
75
|
});
|
|
76
76
|
if (!e.ok)
|
|
@@ -80,7 +80,7 @@ async function Ot() {
|
|
|
80
80
|
throw new Error("getAuthToken returned no token");
|
|
81
81
|
return n;
|
|
82
82
|
}
|
|
83
|
-
async function
|
|
83
|
+
async function Kr(e, t = dt) {
|
|
84
84
|
const n = await fetch(`${t.replace(/\/$/, "")}/api/session-value`, {
|
|
85
85
|
headers: { Authorization: `Bearer ${e}` }
|
|
86
86
|
});
|
|
@@ -90,7 +90,7 @@ async function qr(e, t = ft) {
|
|
|
90
90
|
if (!r.value) throw new Error("Session value response missing value");
|
|
91
91
|
return r;
|
|
92
92
|
}
|
|
93
|
-
function
|
|
93
|
+
function Gr(e) {
|
|
94
94
|
const t = e.trim();
|
|
95
95
|
if (t.length % 2 !== 0) throw new Error("Invalid hex key");
|
|
96
96
|
const n = new Uint8Array(t.length / 2);
|
|
@@ -101,17 +101,17 @@ function Kr(e) {
|
|
|
101
101
|
function yt(e) {
|
|
102
102
|
return Uint8Array.from(e);
|
|
103
103
|
}
|
|
104
|
-
function
|
|
104
|
+
function jr(e, t) {
|
|
105
105
|
const n = new Uint8Array(e.length + t.length);
|
|
106
106
|
return n.set(e, 0), n.set(t, e.length), n;
|
|
107
107
|
}
|
|
108
|
-
async function
|
|
108
|
+
async function zr(e, t) {
|
|
109
109
|
if (!t) throw new Error("Asset key is required for encrypted assets");
|
|
110
110
|
if (e.byteLength < 28)
|
|
111
111
|
throw new Error("Encrypted payload too small");
|
|
112
|
-
const n = new Uint8Array(e), r = yt(n.subarray(0, 12)), s = yt(n.subarray(12, 28)), i = yt(n.subarray(28)), a = yt(
|
|
112
|
+
const n = new Uint8Array(e), r = yt(n.subarray(0, 12)), s = yt(n.subarray(12, 28)), i = yt(n.subarray(28)), a = yt(jr(i, s)), o = await crypto.subtle.importKey(
|
|
113
113
|
"raw",
|
|
114
|
-
|
|
114
|
+
Gr(t),
|
|
115
115
|
{ name: "AES-GCM" },
|
|
116
116
|
!1,
|
|
117
117
|
["decrypt"]
|
|
@@ -134,21 +134,21 @@ function bt(e) {
|
|
|
134
134
|
const s = _t(t) ? t : _t(n) ? n : t;
|
|
135
135
|
return { twinBase: s, binBase: s, encrypted: !0 };
|
|
136
136
|
}
|
|
137
|
-
function
|
|
137
|
+
function et(e) {
|
|
138
138
|
return bt(e).encrypted;
|
|
139
139
|
}
|
|
140
|
-
function
|
|
140
|
+
function kn(e, t = zt) {
|
|
141
141
|
const n = `${t.replace(/\/$/, "")}/${e}`;
|
|
142
142
|
return { twinBase: n, binBase: n, encrypted: !0 };
|
|
143
143
|
}
|
|
144
|
-
function
|
|
144
|
+
function Yr(e, t) {
|
|
145
145
|
return (e ?? t)?.trim() || void 0;
|
|
146
146
|
}
|
|
147
|
-
function
|
|
147
|
+
function Jr(e) {
|
|
148
148
|
Wt = bt(e);
|
|
149
149
|
for (const t of Ht) t();
|
|
150
150
|
}
|
|
151
|
-
function
|
|
151
|
+
function Qr(e, t) {
|
|
152
152
|
const n = typeof globalThis.location < "u" ? globalThis.location.href : void 0;
|
|
153
153
|
if (!n) return bt(e);
|
|
154
154
|
const r = (s) => {
|
|
@@ -164,7 +164,7 @@ function Jr(e, t) {
|
|
|
164
164
|
encrypted: e.encrypted
|
|
165
165
|
});
|
|
166
166
|
}
|
|
167
|
-
function
|
|
167
|
+
function We() {
|
|
168
168
|
if (!Wt)
|
|
169
169
|
throw new Error("Twin assets not configured; call setActiveTwinAssets first");
|
|
170
170
|
return Wt;
|
|
@@ -173,29 +173,29 @@ function Xr(e) {
|
|
|
173
173
|
return Ht.add(e), () => Ht.delete(e);
|
|
174
174
|
}
|
|
175
175
|
function bn() {
|
|
176
|
-
const e =
|
|
177
|
-
return
|
|
178
|
-
}
|
|
179
|
-
function Qr() {
|
|
180
|
-
const e = He();
|
|
181
|
-
return Ze(e) ? `${e.binBase}/idle.bin` : `${e.twinBase}/idle.mp4`;
|
|
176
|
+
const e = We();
|
|
177
|
+
return et(e) ? `${e.binBase}/sil.bin` : `${e.twinBase}/sil.png`;
|
|
182
178
|
}
|
|
183
179
|
function Zr() {
|
|
184
|
-
const e =
|
|
185
|
-
return
|
|
186
|
-
}
|
|
187
|
-
function Mt() {
|
|
188
|
-
return Ze(He());
|
|
180
|
+
const e = We();
|
|
181
|
+
return et(e) ? `${e.binBase}/idle.bin` : `${e.twinBase}/idle.mp4`;
|
|
189
182
|
}
|
|
190
183
|
function es() {
|
|
191
|
-
const e =
|
|
192
|
-
return
|
|
184
|
+
const e = We();
|
|
185
|
+
return et(e) ? e.binBase : e.twinBase;
|
|
186
|
+
}
|
|
187
|
+
function Pt() {
|
|
188
|
+
return et(We());
|
|
193
189
|
}
|
|
194
190
|
function ts() {
|
|
195
|
-
const e =
|
|
196
|
-
return
|
|
191
|
+
const e = We();
|
|
192
|
+
return et(e) ? `${e.binBase}/atlas.bin` : `${e.twinBase}/atlas.json`;
|
|
197
193
|
}
|
|
198
|
-
function
|
|
194
|
+
function ns() {
|
|
195
|
+
const e = We();
|
|
196
|
+
return et(e) ? `${e.binBase}/expression_atlas.bin` : `${e.twinBase}/expression_atlas.json`;
|
|
197
|
+
}
|
|
198
|
+
function Gn(e) {
|
|
199
199
|
const t = e.split(/\r?\n/);
|
|
200
200
|
let n = "", r = "";
|
|
201
201
|
for (const i of t)
|
|
@@ -210,7 +210,7 @@ function Kn(e) {
|
|
|
210
210
|
}
|
|
211
211
|
return { event: n, data: s };
|
|
212
212
|
}
|
|
213
|
-
const
|
|
213
|
+
const rs = [
|
|
214
214
|
"aa",
|
|
215
215
|
"CH",
|
|
216
216
|
"DD",
|
|
@@ -226,14 +226,14 @@ const ns = [
|
|
|
226
226
|
"kk",
|
|
227
227
|
"nn",
|
|
228
228
|
"sil"
|
|
229
|
-
],
|
|
230
|
-
|
|
229
|
+
], ss = new Map(
|
|
230
|
+
rs.map((e) => [e.toLowerCase(), e])
|
|
231
231
|
);
|
|
232
|
-
function
|
|
232
|
+
function is(e) {
|
|
233
233
|
const t = (e ?? "").trim();
|
|
234
|
-
return t ?
|
|
234
|
+
return t ? ss.get(t.toLowerCase()) ?? "sil" : "sil";
|
|
235
235
|
}
|
|
236
|
-
const
|
|
236
|
+
const as = {
|
|
237
237
|
aei: ["aa", "E", "I"],
|
|
238
238
|
o: ["O", "U"],
|
|
239
239
|
ee: ["I"],
|
|
@@ -245,12 +245,12 @@ const is = {
|
|
|
245
245
|
qw: ["U", "O"],
|
|
246
246
|
cdgknstxyz: ["DD", "SS", "kk", "CH"]
|
|
247
247
|
};
|
|
248
|
-
function
|
|
248
|
+
function os(e) {
|
|
249
249
|
if (!e) return ["sil"];
|
|
250
250
|
const t = e.toLowerCase();
|
|
251
|
-
return
|
|
251
|
+
return as[t] ?? ["sil"];
|
|
252
252
|
}
|
|
253
|
-
function
|
|
253
|
+
function cs(e, t) {
|
|
254
254
|
const n = e.word.length;
|
|
255
255
|
if (n <= 0) return 0;
|
|
256
256
|
const r = e.wduration;
|
|
@@ -258,38 +258,38 @@ function os(e, t) {
|
|
|
258
258
|
const s = Math.max(0, Math.min(1, (t - e.wtime) / r));
|
|
259
259
|
return Math.min(n - 1, Math.floor(s * n));
|
|
260
260
|
}
|
|
261
|
-
function
|
|
261
|
+
function Je(e, t) {
|
|
262
262
|
const n = Math.max(0, Math.min(e.length - 1, t));
|
|
263
263
|
return e[n] ?? "";
|
|
264
264
|
}
|
|
265
|
-
function
|
|
265
|
+
function Qt(e, t) {
|
|
266
266
|
const n = e.toLowerCase().replace(/[^a-z']/g, "");
|
|
267
|
-
return !n ||
|
|
267
|
+
return !n || Je(n, t) !== "w" || t > 0 && Je(n, t - 1) === "q" ? !1 : t === 0 && /^w[aeiouy]/.test(n);
|
|
268
268
|
}
|
|
269
|
-
function
|
|
270
|
-
const n = e.toLowerCase(), r =
|
|
269
|
+
function us(e, t) {
|
|
270
|
+
const n = e.toLowerCase(), r = Je(n, t), s = n.slice(Math.max(0, t - 1), t + 2);
|
|
271
271
|
return r === "i" || r === "y" ? "I" : s.includes("ee") || r === "e" || n.includes("ea") ? "E" : "aa";
|
|
272
272
|
}
|
|
273
|
-
function
|
|
273
|
+
function ls(e, t) {
|
|
274
274
|
const n = e.toLowerCase(), r = n.slice(
|
|
275
275
|
Math.max(0, t - 1),
|
|
276
276
|
Math.min(n.length, t + 3)
|
|
277
277
|
);
|
|
278
278
|
if (/oo|ou|uw/.test(r)) return "U";
|
|
279
|
-
if (
|
|
280
|
-
const s =
|
|
279
|
+
if (Qt(n, t)) return "FF";
|
|
280
|
+
const s = Je(n, t);
|
|
281
281
|
return s === "u" || s === "w" ? "U" : "O";
|
|
282
282
|
}
|
|
283
|
-
function
|
|
283
|
+
function fs(e, t) {
|
|
284
284
|
const n = e.toLowerCase();
|
|
285
|
-
if (
|
|
285
|
+
if (Qt(n, t)) return "FF";
|
|
286
286
|
const r = n.slice(Math.max(0, t - 2), t + 1);
|
|
287
287
|
if (/qu/.test(r)) return "U";
|
|
288
288
|
const s = n.slice(
|
|
289
289
|
Math.max(0, t - 1),
|
|
290
290
|
Math.min(n.length, t + 3)
|
|
291
291
|
);
|
|
292
|
-
return /wo|wh/.test(s) ||
|
|
292
|
+
return /wo|wh/.test(s) || Je(n, t) === "o" ? "O" : "U";
|
|
293
293
|
}
|
|
294
294
|
const St = {
|
|
295
295
|
d: "DD",
|
|
@@ -303,8 +303,8 @@ const St = {
|
|
|
303
303
|
x: "CH",
|
|
304
304
|
j: "CH"
|
|
305
305
|
};
|
|
306
|
-
function
|
|
307
|
-
const n = e.toLowerCase(), r =
|
|
306
|
+
function ds(e, t) {
|
|
307
|
+
const n = e.toLowerCase(), r = Je(n, t);
|
|
308
308
|
if (St[r]) return St[r];
|
|
309
309
|
for (let s = 0; s < n.length; s++) {
|
|
310
310
|
const i = n[s];
|
|
@@ -312,33 +312,33 @@ function fs(e, t) {
|
|
|
312
312
|
}
|
|
313
313
|
return "DD";
|
|
314
314
|
}
|
|
315
|
-
function
|
|
316
|
-
const r =
|
|
315
|
+
function ms(e, t, n) {
|
|
316
|
+
const r = os(e);
|
|
317
317
|
if (r.length === 1) return r[0];
|
|
318
318
|
const s = t.trim();
|
|
319
319
|
if (!s) return r[0];
|
|
320
320
|
const i = (e ?? "").toLowerCase(), a = Math.max(0, n);
|
|
321
321
|
switch (i) {
|
|
322
322
|
case "aei":
|
|
323
|
-
return cs(s, a);
|
|
324
|
-
case "o":
|
|
325
323
|
return us(s, a);
|
|
326
|
-
case "
|
|
324
|
+
case "o":
|
|
327
325
|
return ls(s, a);
|
|
328
|
-
case "
|
|
326
|
+
case "qw":
|
|
329
327
|
return fs(s, a);
|
|
328
|
+
case "cdgknstxyz":
|
|
329
|
+
return ds(s, a);
|
|
330
330
|
default:
|
|
331
331
|
return r[0];
|
|
332
332
|
}
|
|
333
333
|
}
|
|
334
|
-
const
|
|
335
|
-
function
|
|
334
|
+
const hs = 32, En = 48;
|
|
335
|
+
function jn(e) {
|
|
336
336
|
let t = 0;
|
|
337
337
|
for (const n of e)
|
|
338
338
|
t = Math.max(t, n.vtime + n.vduration);
|
|
339
339
|
return t;
|
|
340
340
|
}
|
|
341
|
-
function
|
|
341
|
+
function zn(e) {
|
|
342
342
|
let t = null, n = -1;
|
|
343
343
|
for (const r of e) {
|
|
344
344
|
if (r.viseme === "sil") continue;
|
|
@@ -347,22 +347,22 @@ function jn(e) {
|
|
|
347
347
|
}
|
|
348
348
|
return t;
|
|
349
349
|
}
|
|
350
|
-
function
|
|
351
|
-
return
|
|
350
|
+
function ps(e) {
|
|
351
|
+
return Yn(e).find((n) => n.viseme !== "sil") ?? null;
|
|
352
352
|
}
|
|
353
353
|
function Ne(e) {
|
|
354
|
-
const t =
|
|
355
|
-
return
|
|
354
|
+
const t = jn(e);
|
|
355
|
+
return zn(e) ? t + Yt : t;
|
|
356
356
|
}
|
|
357
|
-
function
|
|
358
|
-
const t = [], n =
|
|
357
|
+
function ws(e) {
|
|
358
|
+
const t = [], n = ps(e);
|
|
359
359
|
n && n.vtime > 0 && t.push({
|
|
360
360
|
from: "sil",
|
|
361
361
|
to: n.viseme,
|
|
362
362
|
fromVtime: 0,
|
|
363
363
|
toVtime: n.vtime
|
|
364
364
|
});
|
|
365
|
-
const r =
|
|
365
|
+
const r = zn(e), s = jn(e);
|
|
366
366
|
return r && t.push({
|
|
367
367
|
from: r.viseme,
|
|
368
368
|
to: "sil",
|
|
@@ -370,54 +370,70 @@ function ps(e) {
|
|
|
370
370
|
toVtime: s + Yt
|
|
371
371
|
}), t;
|
|
372
372
|
}
|
|
373
|
-
function
|
|
373
|
+
function Yn(e) {
|
|
374
374
|
const t = /* @__PURE__ */ new Map();
|
|
375
375
|
for (const n of e)
|
|
376
376
|
t.has(n.vtime) || t.set(n.vtime, n);
|
|
377
377
|
return [...t.values()].sort((n, r) => n.vtime - r.vtime);
|
|
378
378
|
}
|
|
379
|
-
function
|
|
380
|
-
const t =
|
|
379
|
+
function gs(e) {
|
|
380
|
+
const t = Yn(e), n = [];
|
|
381
381
|
for (let r = 0; r < t.length - 1; r++) {
|
|
382
382
|
const s = t[r].viseme, i = t[r + 1].viseme, a = t[r].vtime, o = t[r + 1].vtime;
|
|
383
383
|
s === i || o <= a || n.push({ from: s, to: i, fromVtime: a, toVtime: o });
|
|
384
384
|
}
|
|
385
385
|
return n;
|
|
386
386
|
}
|
|
387
|
-
function
|
|
387
|
+
function ys(e) {
|
|
388
388
|
return e.length === 0 ? [] : [
|
|
389
|
-
...
|
|
390
|
-
...
|
|
389
|
+
...ws(e),
|
|
390
|
+
...gs(e)
|
|
391
391
|
];
|
|
392
392
|
}
|
|
393
|
-
function
|
|
393
|
+
function _s(e, t) {
|
|
394
394
|
let n = null;
|
|
395
395
|
for (const r of e) {
|
|
396
|
-
const {
|
|
397
|
-
|
|
396
|
+
const { transStart: s, transEnd: i } = Jn(
|
|
397
|
+
r.fromVtime,
|
|
398
|
+
r.toVtime,
|
|
399
|
+
r.from,
|
|
400
|
+
r.to
|
|
401
|
+
);
|
|
402
|
+
t >= s && t < i && (n = r);
|
|
398
403
|
}
|
|
399
404
|
return n;
|
|
400
405
|
}
|
|
401
|
-
function
|
|
402
|
-
const
|
|
403
|
-
|
|
406
|
+
function Jn(e, t, n, r) {
|
|
407
|
+
const s = Math.max(0, t - e);
|
|
408
|
+
if ((n === "PP" || r === "PP") && s > En) {
|
|
409
|
+
const f = En, c = t, u = c - f;
|
|
410
|
+
return {
|
|
411
|
+
gapMs: s,
|
|
412
|
+
effectiveGapMs: f,
|
|
413
|
+
holdEnd: u,
|
|
414
|
+
transStart: u,
|
|
415
|
+
transEnd: c
|
|
416
|
+
};
|
|
417
|
+
}
|
|
418
|
+
const a = s > 0 ? Math.max(s, hs) : 0, o = e, d = e + a;
|
|
419
|
+
return { gapMs: s, effectiveGapMs: a, holdEnd: e, transStart: o, transEnd: d };
|
|
404
420
|
}
|
|
405
|
-
const
|
|
406
|
-
function
|
|
421
|
+
const Xt = 16e3;
|
|
422
|
+
function Qn(e) {
|
|
407
423
|
const t = Number(e);
|
|
408
|
-
return Number.isFinite(t) && t > 0 ? t :
|
|
424
|
+
return Number.isFinite(t) && t > 0 ? t : Xt;
|
|
409
425
|
}
|
|
410
|
-
function
|
|
426
|
+
function Ss(e) {
|
|
411
427
|
let t = e.trim();
|
|
412
428
|
const n = t.indexOf(",");
|
|
413
429
|
t.startsWith("data:") && n >= 0 && (t = t.slice(n + 1)), t = t.replace(/\s+/g, "").replace(/-/g, "+").replace(/_/g, "/");
|
|
414
430
|
const r = t.length % 4;
|
|
415
431
|
return r !== 0 && (t += "=".repeat(4 - r)), t;
|
|
416
432
|
}
|
|
417
|
-
function
|
|
433
|
+
function vs(e) {
|
|
418
434
|
return e.length >= 4 && e[0] === 82 && e[1] === 73 && e[2] === 70 && e[3] === 70;
|
|
419
435
|
}
|
|
420
|
-
function
|
|
436
|
+
function Tn(e, t, n = Xt) {
|
|
421
437
|
const r = t.byteOffset % 2 === 0 ? t : t.slice(), s = new Int16Array(
|
|
422
438
|
r.buffer,
|
|
423
439
|
r.byteOffset,
|
|
@@ -429,14 +445,14 @@ function En(e, t, n = Qt) {
|
|
|
429
445
|
return a.copyToChannel(i, 0), a;
|
|
430
446
|
}
|
|
431
447
|
function ks(e) {
|
|
432
|
-
const t =
|
|
448
|
+
const t = Ss(e), n = window.atob(t), r = new Uint8Array(n.length);
|
|
433
449
|
for (let s = 0; s < n.length; s++)
|
|
434
450
|
r[s] = n.charCodeAt(s);
|
|
435
451
|
return r;
|
|
436
452
|
}
|
|
437
|
-
async function
|
|
438
|
-
const r = ks(t), s =
|
|
439
|
-
if (
|
|
453
|
+
async function An(e, t, n = Xt) {
|
|
454
|
+
const r = ks(t), s = Qn(n);
|
|
455
|
+
if (vs(r)) {
|
|
440
456
|
const i = r.buffer.slice(
|
|
441
457
|
r.byteOffset,
|
|
442
458
|
r.byteOffset + r.byteLength
|
|
@@ -444,7 +460,7 @@ async function vs(e, t, n = Qt) {
|
|
|
444
460
|
return e.decodeAudioData(i);
|
|
445
461
|
}
|
|
446
462
|
if (r.length >= 2 && r.length % 2 === 0)
|
|
447
|
-
return
|
|
463
|
+
return Tn(e, r, s);
|
|
448
464
|
try {
|
|
449
465
|
const i = r.buffer.slice(
|
|
450
466
|
r.byteOffset,
|
|
@@ -452,15 +468,9 @@ async function vs(e, t, n = Qt) {
|
|
|
452
468
|
);
|
|
453
469
|
return await e.decodeAudioData(i);
|
|
454
470
|
} catch {
|
|
455
|
-
return
|
|
471
|
+
return Tn(e, r, s);
|
|
456
472
|
}
|
|
457
473
|
}
|
|
458
|
-
function Tn(e) {
|
|
459
|
-
let t = 0;
|
|
460
|
-
for (const n of e)
|
|
461
|
-
t = Math.max(t, n.vtime + n.vduration);
|
|
462
|
-
return t;
|
|
463
|
-
}
|
|
464
474
|
function bs(e, t) {
|
|
465
475
|
for (const n of e)
|
|
466
476
|
if (t >= n.wtime && t < n.wtime + n.wduration)
|
|
@@ -469,312 +479,295 @@ function bs(e, t) {
|
|
|
469
479
|
}
|
|
470
480
|
function Xn(e, t) {
|
|
471
481
|
const n = [], r = [];
|
|
472
|
-
let s = null, i = !1, a = !1, o = !1, d = !1,
|
|
473
|
-
const
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
477
|
-
},
|
|
478
|
-
|
|
482
|
+
let s = null, i = !1, a = !1, o = !1, d = !1, f = 0, c = 0, u = 0, m = null, g = 1, E = t, h = !1, D = null, _ = 0, P = !1, p = !1, k = 0, x = null, R = null, K = null;
|
|
483
|
+
const B = () => ({
|
|
484
|
+
visemes: [],
|
|
485
|
+
words: [],
|
|
486
|
+
segmentOffsetMs: 0
|
|
487
|
+
}), S = () => {
|
|
488
|
+
p = !1, k = 0;
|
|
489
|
+
}, b = () => {
|
|
490
|
+
m != null && (clearTimeout(m), m = null);
|
|
491
|
+
}, A = () => {
|
|
492
|
+
for (const w of r) {
|
|
479
493
|
try {
|
|
480
|
-
|
|
494
|
+
w.onended = null, w.stop(0);
|
|
481
495
|
} catch {
|
|
482
496
|
}
|
|
483
497
|
try {
|
|
484
|
-
|
|
498
|
+
w.disconnect();
|
|
485
499
|
} catch {
|
|
486
500
|
}
|
|
487
501
|
}
|
|
488
502
|
r.length = 0;
|
|
503
|
+
}, ne = () => {
|
|
504
|
+
for (const w of r)
|
|
505
|
+
w.playbackRate.value = g;
|
|
489
506
|
}, M = () => {
|
|
490
|
-
|
|
491
|
-
g.playbackRate.value = b;
|
|
492
|
-
}, Q = () => Math.max(_, h), x = () => {
|
|
493
|
-
if (!(P || !d || i || r.length > 0 || n.length > 0)) {
|
|
507
|
+
if (!(h || !d || i || p || r.length > 0 || n.length > 0)) {
|
|
494
508
|
if (o && s && c > 0) {
|
|
495
|
-
const
|
|
496
|
-
if (
|
|
497
|
-
|
|
498
|
-
const
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
}, Math.max(0,
|
|
509
|
+
const w = (s.currentTime - c) * 1e3;
|
|
510
|
+
if (w < _) {
|
|
511
|
+
b();
|
|
512
|
+
const I = g > 0 ? (_ - w) / g : _ - w;
|
|
513
|
+
m = setTimeout(() => {
|
|
514
|
+
h || (a = !1, m = null, e.onSpeakingDone(), e.onNotify());
|
|
515
|
+
}, Math.max(0, I));
|
|
502
516
|
return;
|
|
503
517
|
}
|
|
504
518
|
}
|
|
505
|
-
a = !1,
|
|
519
|
+
a = !1, b(), e.onSpeakingDone(), e.onNotify();
|
|
506
520
|
}
|
|
507
|
-
},
|
|
508
|
-
const
|
|
509
|
-
if (
|
|
521
|
+
}, Y = (w) => {
|
|
522
|
+
const I = Ne(w);
|
|
523
|
+
if (I <= 0) {
|
|
510
524
|
e.onSpeakingDone(), e.onNotify();
|
|
511
525
|
return;
|
|
512
526
|
}
|
|
513
|
-
a = !0,
|
|
514
|
-
const
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
},
|
|
518
|
-
},
|
|
519
|
-
|
|
520
|
-
const
|
|
521
|
-
if (!
|
|
522
|
-
const
|
|
523
|
-
|
|
524
|
-
word:
|
|
525
|
-
wtime: u +
|
|
526
|
-
wduration:
|
|
527
|
-
queueIndex:
|
|
528
|
-
gesture:
|
|
529
|
-
emphasis:
|
|
527
|
+
a = !0, f = performance.now(), e.onSpeakingStart(), e.onNotify(), b();
|
|
528
|
+
const T = g > 0 ? I / g : I;
|
|
529
|
+
m = setTimeout(() => {
|
|
530
|
+
h || (a = !1, m = null, e.onSpeakingDone(), e.onNotify());
|
|
531
|
+
}, T);
|
|
532
|
+
}, X = (w, I, T, U) => {
|
|
533
|
+
I.length !== 0 && (u = T, I.forEach((F) => {
|
|
534
|
+
const ee = String(F.word ?? "").trim();
|
|
535
|
+
if (!ee) return;
|
|
536
|
+
const j = Math.round((F.start ?? 0) * 1e3), q = F.duration != null ? Math.round(F.duration * 1e3) : F.end != null ? Math.max(1, Math.round((F.end - (F.start ?? 0)) * 1e3)) : 0;
|
|
537
|
+
w.push({
|
|
538
|
+
word: ee,
|
|
539
|
+
wtime: u + j,
|
|
540
|
+
wduration: q,
|
|
541
|
+
queueIndex: w.length,
|
|
542
|
+
gesture: F.gesture ?? null,
|
|
543
|
+
emphasis: F.emphasis === !0
|
|
530
544
|
});
|
|
531
545
|
}));
|
|
532
|
-
},
|
|
533
|
-
|
|
534
|
-
const
|
|
535
|
-
if (!
|
|
536
|
-
const
|
|
537
|
-
let
|
|
538
|
-
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
),
|
|
543
|
-
viseme:
|
|
546
|
+
}, ae = (w, I, T, U, F, te) => {
|
|
547
|
+
T.length !== 0 && (u = U, T.forEach((ee) => {
|
|
548
|
+
const j = String(ee.symbol ?? ee.viseme ?? "").trim();
|
|
549
|
+
if (!j) return;
|
|
550
|
+
const q = Math.round((ee.start ?? 0) * 1e3), De = Math.max(1, Math.round((ee.duration ?? 0) * 1e3)), He = u + q, ke = bs(I, He), $e = ke ? cs(ke, He) : 0;
|
|
551
|
+
let Re;
|
|
552
|
+
Lr(te) === "oculus_direct" ? (Re = is(j), Re === "U" && ke && Qt(ke.word, $e) && (Re = "FF")) : Re = ms(
|
|
553
|
+
j,
|
|
554
|
+
ke?.word ?? "",
|
|
555
|
+
$e
|
|
556
|
+
), w.push({
|
|
557
|
+
viseme: Re,
|
|
544
558
|
weight: 1,
|
|
545
|
-
vtime:
|
|
546
|
-
vduration:
|
|
559
|
+
vtime: He,
|
|
560
|
+
vduration: De
|
|
547
561
|
});
|
|
548
562
|
}), e.onNotify());
|
|
549
|
-
},
|
|
550
|
-
|
|
551
|
-
|
|
552
|
-
|
|
553
|
-
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
563
|
+
}, Z = (w, I, T, U, F, te, ee) => {
|
|
564
|
+
X(I, U, F), ae(
|
|
565
|
+
w,
|
|
566
|
+
I,
|
|
567
|
+
T,
|
|
568
|
+
F,
|
|
569
|
+
te,
|
|
570
|
+
ee
|
|
557
571
|
);
|
|
558
|
-
},
|
|
559
|
-
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
a = !0, e.onSpeakingStart(), S?.isFirstOfStream ? (c = D, u = 0, S.onNewStream?.()) : c <= 0 && (c = D);
|
|
571
|
-
const Z = (D - W) * 1e3;
|
|
572
|
-
m = performance.now() + Z;
|
|
572
|
+
}, de = (w, I, T) => {
|
|
573
|
+
K === w && w.visemes === I || (I.length = 0, T.length = 0, w.visemes = I, w.words = T, w.segmentOffsetMs = 0, K = w, u = 0, _ = 0);
|
|
574
|
+
}, fe = async () => {
|
|
575
|
+
const w = window.AudioContext || window.webkitAudioContext;
|
|
576
|
+
return s || (s = new w()), s.state === "suspended" && await s.resume(), D || (D = s.createMediaStreamDestination()), s;
|
|
577
|
+
}, me = (w, I) => {
|
|
578
|
+
if (!s) return 0;
|
|
579
|
+
const T = s, U = T.currentTime, F = U + 0.02;
|
|
580
|
+
if (I.isFirstAudio) {
|
|
581
|
+
c <= 0 && (c = F);
|
|
582
|
+
const ee = (F - U) * 1e3;
|
|
583
|
+
f = performance.now() + ee;
|
|
573
584
|
}
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
|
|
578
|
-
h,
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
if (
|
|
583
|
-
|
|
584
|
-
const g = G.splice(0);
|
|
585
|
-
B = 0;
|
|
586
|
-
for (let S = 0; S < g.length; S++)
|
|
587
|
-
he(g[S].audioBuffer, {
|
|
588
|
-
isFirstAudio: S === 0 && !a,
|
|
589
|
-
isFirstOfStream: S === 0
|
|
590
|
-
});
|
|
591
|
-
e.onNotify();
|
|
592
|
-
}, de = async (g, S, L, W, D, R, T) => {
|
|
593
|
-
if (P) return;
|
|
594
|
-
const Z = Jn(T?.sampleRate), ae = T?.newStream === !0;
|
|
595
|
-
if (!L?.trim()) {
|
|
596
|
-
if (W.length === 0 && D.length === 0) return;
|
|
597
|
-
ae && (u = 0, _ = 0, h = 0, g.length = 0, S.length = 0, T?.onNewStream?.());
|
|
598
|
-
let te = T?.audioOffsetMs != null ? T.audioOffsetMs : u;
|
|
599
|
-
T?.audioOffsetMs == null && R && g.length > 0 && !ae && (te = Tn(g));
|
|
600
|
-
const ue = T?.audioOffsetMs != null ? !0 : R;
|
|
601
|
-
X(
|
|
602
|
-
g,
|
|
603
|
-
S,
|
|
604
|
-
W,
|
|
605
|
-
D,
|
|
606
|
-
te,
|
|
607
|
-
ue,
|
|
608
|
-
p
|
|
609
|
-
), _ = Math.max(_, Ne(g)), !a && _ > 0 && z(g), e.onNotify();
|
|
610
|
-
return;
|
|
611
|
-
}
|
|
612
|
-
if (i) {
|
|
613
|
-
n.push({
|
|
614
|
-
audio: L,
|
|
615
|
-
visemes: W,
|
|
616
|
-
words: D,
|
|
617
|
-
isNewSegment: R,
|
|
618
|
-
sampleRate: Z,
|
|
619
|
-
newStream: ae,
|
|
620
|
-
audioOffsetMs: T?.audioOffsetMs
|
|
621
|
-
});
|
|
585
|
+
I.onBeforeStart?.(F);
|
|
586
|
+
const te = T.createBufferSource();
|
|
587
|
+
return te.buffer = w, te.playbackRate.value = g, te.connect(T.destination), D && te.connect(D), r.push(te), h ? (r.pop(), F) : (I.isFirstAudio && (a = !0, e.onSpeakingStart()), te.onended = () => {
|
|
588
|
+
const ee = r.indexOf(te);
|
|
589
|
+
ee >= 0 && r.splice(ee, 1), e.onNotify(), !h && (x && R ? J(x, R) : M());
|
|
590
|
+
}, te.start(F), F);
|
|
591
|
+
}, J = async (w, I) => {
|
|
592
|
+
if (h || i || r.length > 0) return;
|
|
593
|
+
if (n.length === 0) {
|
|
594
|
+
M();
|
|
622
595
|
return;
|
|
623
596
|
}
|
|
624
597
|
i = !0;
|
|
598
|
+
let T = !1;
|
|
625
599
|
try {
|
|
626
|
-
const
|
|
627
|
-
|
|
628
|
-
const
|
|
629
|
-
|
|
630
|
-
const
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
|
|
638
|
-
|
|
639
|
-
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
644
|
-
|
|
645
|
-
|
|
646
|
-
|
|
647
|
-
|
|
648
|
-
|
|
600
|
+
const U = await fe();
|
|
601
|
+
if (h) return;
|
|
602
|
+
const F = n[0];
|
|
603
|
+
if (!F) return;
|
|
604
|
+
const te = !a;
|
|
605
|
+
if (P && (e.shouldHoldForWarmup?.() ?? !1) && (p || te && F.newStream) || p) {
|
|
606
|
+
de(F.utterance, w, I);
|
|
607
|
+
for (const q of n) {
|
|
608
|
+
if (h) return;
|
|
609
|
+
q.audioBuffer || (q.audioBuffer = await An(
|
|
610
|
+
U,
|
|
611
|
+
q.audio,
|
|
612
|
+
q.sampleRate
|
|
613
|
+
)), o = !0, p || (p = !0, k = 0, q.newStream && q.onNewStream?.()), q.visemesQueued || (Z(
|
|
614
|
+
w,
|
|
615
|
+
I,
|
|
616
|
+
q.visemes,
|
|
617
|
+
q.words,
|
|
618
|
+
k,
|
|
619
|
+
!0,
|
|
620
|
+
E
|
|
621
|
+
), q.visemesQueued = !0, k += Math.round(q.audioBuffer.duration * 1e3), _ = Math.max(
|
|
622
|
+
_,
|
|
623
|
+
Ne(w)
|
|
624
|
+
));
|
|
625
|
+
}
|
|
626
|
+
e.onNotify();
|
|
649
627
|
return;
|
|
650
628
|
}
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
isFirstAudio:
|
|
659
|
-
isFirstOfStream:
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
|
|
670
|
-
console.error("[avatarChunkPlayback] audio chunk failed:", te);
|
|
671
|
-
} finally {
|
|
672
|
-
if (i = !1, P) return;
|
|
673
|
-
const te = n.shift();
|
|
674
|
-
te ? await de(
|
|
675
|
-
g,
|
|
676
|
-
S,
|
|
677
|
-
te.audio,
|
|
678
|
-
te.visemes,
|
|
679
|
-
te.words,
|
|
680
|
-
te.isNewSegment,
|
|
681
|
-
{
|
|
682
|
-
sampleRate: te.sampleRate,
|
|
683
|
-
newStream: te.newStream,
|
|
684
|
-
audioOffsetMs: te.audioOffsetMs,
|
|
685
|
-
onNewStream: T?.onNewStream
|
|
629
|
+
const j = n.shift();
|
|
630
|
+
if (!j || (j.audioBuffer || (j.audioBuffer = await An(
|
|
631
|
+
U,
|
|
632
|
+
j.audio,
|
|
633
|
+
j.sampleRate
|
|
634
|
+
)), h)) return;
|
|
635
|
+
o = !0, b(), de(j.utterance, w, I), j.visemesQueued = !1, j.newStream && j.onNewStream?.(), me(j.audioBuffer, {
|
|
636
|
+
isFirstAudio: !a,
|
|
637
|
+
isFirstOfStream: !1,
|
|
638
|
+
onBeforeStart: (q) => {
|
|
639
|
+
c = q, u = 0, f = performance.now() + (q - U.currentTime) * 1e3, Z(
|
|
640
|
+
w,
|
|
641
|
+
I,
|
|
642
|
+
j.visemes,
|
|
643
|
+
j.words,
|
|
644
|
+
0,
|
|
645
|
+
!0,
|
|
646
|
+
E
|
|
647
|
+
), j.visemesQueued = !0, j.utterance.segmentOffsetMs = 0;
|
|
686
648
|
}
|
|
687
|
-
)
|
|
649
|
+
}), T = r.length > 0, _ = Ne(w), e.onNotify();
|
|
650
|
+
} catch (U) {
|
|
651
|
+
console.error("[avatarChunkPlayback] audio chunk failed:", U);
|
|
652
|
+
} finally {
|
|
653
|
+
if (i = !1, h) return;
|
|
654
|
+
if (p) {
|
|
655
|
+
n.some(
|
|
656
|
+
(F) => !F.audioBuffer || !F.visemesQueued
|
|
657
|
+
) && J(w, I);
|
|
658
|
+
return;
|
|
659
|
+
}
|
|
660
|
+
!T && r.length === 0 && n.length > 0 ? J(w, I) : r.length === 0 && n.length === 0 && M();
|
|
688
661
|
}
|
|
689
662
|
};
|
|
690
663
|
return {
|
|
691
|
-
setStreamTtsEngineId: (
|
|
692
|
-
|
|
664
|
+
setStreamTtsEngineId: (w) => {
|
|
665
|
+
E = w;
|
|
666
|
+
},
|
|
667
|
+
setPlaybackSpeed: (w) => {
|
|
668
|
+
g = Math.max(0.1, Math.min(1, w)), ne();
|
|
693
669
|
},
|
|
694
|
-
|
|
695
|
-
|
|
670
|
+
getPlaybackSpeed: () => g,
|
|
671
|
+
setLipsyncWarmupHoldEnabled: (w) => {
|
|
672
|
+
P = w, w || S();
|
|
696
673
|
},
|
|
697
|
-
|
|
698
|
-
|
|
699
|
-
|
|
674
|
+
isWarmingUp: () => p,
|
|
675
|
+
releaseWarmupHold: () => {
|
|
676
|
+
p && (p = !1, k = 0, x && R && J(x, R), e.onNotify());
|
|
700
677
|
},
|
|
701
|
-
|
|
702
|
-
|
|
703
|
-
resetForNewStream: (g) => {
|
|
704
|
-
P = !1, d = !1, p = g, _ = 0, h = 0;
|
|
678
|
+
resetForNewStream: (w) => {
|
|
679
|
+
h = !1, d = !1, E = w, _ = 0;
|
|
705
680
|
},
|
|
706
681
|
/** Next sentence in the same bot turn — keep viseme tail, allow more chunks. */
|
|
707
682
|
resumeBotStream: () => {
|
|
708
|
-
|
|
683
|
+
h = !1, d = !1;
|
|
709
684
|
},
|
|
710
685
|
/** After interrupt — allow the next utterance to queue/play again. */
|
|
711
686
|
clearAborted: () => {
|
|
712
|
-
|
|
687
|
+
h = !1;
|
|
713
688
|
},
|
|
714
689
|
/** Call from a user gesture before bot audio (connect / unlock). */
|
|
715
690
|
primeAudioContext: async () => {
|
|
716
|
-
const
|
|
717
|
-
s || (s = new
|
|
691
|
+
const w = window.AudioContext || window.webkitAudioContext;
|
|
692
|
+
s || (s = new w()), s.state === "suspended" && await s.resume(), s && !D && (D = s.createMediaStreamDestination());
|
|
718
693
|
},
|
|
719
694
|
stop: () => {
|
|
720
|
-
|
|
695
|
+
h = !0, b(), A(), n.length = 0, i = !1, a = !1, o = !1, d = !1, u = 0, c = 0, f = 0, _ = 0, x = null, R = null, K = null, S();
|
|
721
696
|
},
|
|
722
|
-
markStreamComplete: (
|
|
723
|
-
if (_ = Math.max(_, Ne(
|
|
724
|
-
|
|
697
|
+
markStreamComplete: (w) => {
|
|
698
|
+
if (_ = Math.max(_, Ne(w)), d = !0, !o && w.length > 0) {
|
|
699
|
+
Y(w);
|
|
700
|
+
return;
|
|
701
|
+
}
|
|
702
|
+
M();
|
|
703
|
+
},
|
|
704
|
+
playAudioChunk: async (w, I, T, U, F, te, ee) => {
|
|
705
|
+
if (h) return;
|
|
706
|
+
x = w, R = I;
|
|
707
|
+
const j = Qn(ee?.sampleRate), q = ee?.newStream === !0, De = B();
|
|
708
|
+
if (!T?.trim()) {
|
|
709
|
+
if (U.length === 0 && F.length === 0) return;
|
|
710
|
+
de(De, w, I), q && ee?.onNewStream?.(), Z(
|
|
711
|
+
w,
|
|
712
|
+
I,
|
|
713
|
+
U,
|
|
714
|
+
F,
|
|
715
|
+
0,
|
|
716
|
+
!0,
|
|
717
|
+
E
|
|
718
|
+
), _ = Ne(w), !a && _ > 0 && Y(w), e.onNotify();
|
|
725
719
|
return;
|
|
726
720
|
}
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
721
|
+
n.push({
|
|
722
|
+
audio: T,
|
|
723
|
+
audioBuffer: null,
|
|
724
|
+
utterance: De,
|
|
725
|
+
visemes: U,
|
|
726
|
+
words: F,
|
|
727
|
+
isNewSegment: te,
|
|
728
|
+
sampleRate: j,
|
|
729
|
+
newStream: q,
|
|
730
|
+
onNewStream: ee?.onNewStream,
|
|
731
|
+
visemesQueued: !1
|
|
732
|
+
}), await J(w, I);
|
|
733
|
+
},
|
|
734
|
+
queueTimingsOnly: (w, I, T, U, F) => {
|
|
735
|
+
if (h) return;
|
|
736
|
+
const te = B();
|
|
737
|
+
de(te, w, I), Z(
|
|
738
|
+
w,
|
|
739
|
+
I,
|
|
740
740
|
T,
|
|
741
|
-
|
|
742
|
-
|
|
743
|
-
|
|
741
|
+
U,
|
|
742
|
+
0,
|
|
743
|
+
!0,
|
|
744
|
+
E
|
|
745
|
+
), te.segmentOffsetMs = 0, _ = Ne(w);
|
|
744
746
|
},
|
|
745
747
|
getPlaybackElapsedMs: () => o && s && c > 0 ? Math.max(
|
|
746
748
|
0,
|
|
747
749
|
(s.currentTime - c) * 1e3
|
|
748
|
-
) : a ? Math.max(0, (performance.now() -
|
|
749
|
-
isSpeaking: () => a ? !0 : !o || !s || c <= 0 ? !1 : (s.currentTime - c) * 1e3 <
|
|
750
|
-
getVoiceStream: () =>
|
|
751
|
-
getPlaybackStartPerf: () =>
|
|
750
|
+
) : a ? Math.max(0, (performance.now() - f) * g) : 0,
|
|
751
|
+
isSpeaking: () => a ? !0 : !o || !s || c <= 0 ? !1 : (s.currentTime - c) * 1e3 < _,
|
|
752
|
+
getVoiceStream: () => D ? D.stream : null,
|
|
753
|
+
getPlaybackStartPerf: () => f,
|
|
752
754
|
/** User spoke over the bot — drop in-flight chunks until the next utterance. */
|
|
753
755
|
bargeIn: () => {
|
|
754
|
-
|
|
756
|
+
h = !0, d = !1, b(), A(), n.length = 0, i = !1, a = !1, o = !1, u = 0, c = 0, f = 0, _ = 0, x = null, R = null, K = null, S();
|
|
755
757
|
},
|
|
756
758
|
interrupt: () => {
|
|
757
|
-
|
|
759
|
+
h = !0, d = !1, b(), A(), n.length = 0, i = !1, a = !1, o = !1, u = 0, c = 0, f = 0, _ = 0, x = null, R = null, K = null, S();
|
|
758
760
|
}
|
|
759
761
|
};
|
|
760
762
|
}
|
|
761
|
-
function
|
|
763
|
+
function Mt(e, t) {
|
|
762
764
|
let n = null;
|
|
763
765
|
for (const r of e)
|
|
764
766
|
t < r.vtime || t >= r.vtime + r.vduration || (!n || r.vtime >= n.vtime) && (n = r);
|
|
765
|
-
|
|
766
|
-
let r = null, s = -1;
|
|
767
|
-
for (const i of e) {
|
|
768
|
-
if (i.viseme === "sil") continue;
|
|
769
|
-
const a = i.vtime + i.vduration;
|
|
770
|
-
a <= t && a >= s && (r = i, s = a);
|
|
771
|
-
}
|
|
772
|
-
return r?.viseme ?? "sil";
|
|
773
|
-
}
|
|
774
|
-
return n.viseme;
|
|
767
|
+
return n ? n.viseme : "sil";
|
|
775
768
|
}
|
|
776
|
-
function
|
|
777
|
-
const r =
|
|
769
|
+
function Zn(e, t, n = 120) {
|
|
770
|
+
const r = Mt(e, t);
|
|
778
771
|
if (r !== "sil") return r;
|
|
779
772
|
let s = null;
|
|
780
773
|
for (const i of e) {
|
|
@@ -808,208 +801,207 @@ function Ts(e, t) {
|
|
|
808
801
|
return null;
|
|
809
802
|
}
|
|
810
803
|
}
|
|
811
|
-
const Zt = 0.5, en = 1.5,
|
|
812
|
-
function
|
|
804
|
+
const Zt = 0.5, en = 1.5, er = "Olivia", tr = "f786b574-daa5-4673-aa0c-cbe3e8534c02", Dt = 0.85;
|
|
805
|
+
function In(e, t = dt, n = {}) {
|
|
813
806
|
const r = `${t.replace(/\/$/, "")}/avatar_ttsWithPoses`, s = [], i = [], a = [], o = [];
|
|
814
|
-
let d = "",
|
|
815
|
-
const
|
|
816
|
-
let
|
|
817
|
-
const
|
|
818
|
-
let
|
|
819
|
-
const
|
|
807
|
+
let d = "", f = "neutral", c = "", u = Ye;
|
|
808
|
+
const m = /* @__PURE__ */ new Set();
|
|
809
|
+
let g = 0, E = null;
|
|
810
|
+
const h = () => m.forEach((B) => B());
|
|
811
|
+
let D = () => !1;
|
|
812
|
+
const _ = Xn(
|
|
820
813
|
{
|
|
821
814
|
onSpeakingStart: () => e("speaking"),
|
|
822
815
|
onSpeakingDone: () => e("done"),
|
|
823
|
-
onNotify:
|
|
824
|
-
shouldHoldForWarmup: () =>
|
|
816
|
+
onNotify: h,
|
|
817
|
+
shouldHoldForWarmup: () => D()
|
|
825
818
|
},
|
|
826
|
-
|
|
827
|
-
),
|
|
819
|
+
Ye
|
|
820
|
+
), P = () => _.getPlaybackElapsedMs(), p = (B, S = d) => {
|
|
828
821
|
if (!n.onLipsyncDebug) return;
|
|
829
|
-
const
|
|
822
|
+
const b = P(), A = s;
|
|
830
823
|
n.onLipsyncDebug({
|
|
831
|
-
event:
|
|
832
|
-
spokenText:
|
|
833
|
-
mood:
|
|
834
|
-
playbackAnchorPerf:
|
|
835
|
-
playbackElapsedMs:
|
|
836
|
-
queueLength:
|
|
837
|
-
activeViseme:
|
|
838
|
-
segments: o.map((
|
|
839
|
-
...
|
|
840
|
-
visemes: [...
|
|
824
|
+
event: B,
|
|
825
|
+
spokenText: S,
|
|
826
|
+
mood: f,
|
|
827
|
+
playbackAnchorPerf: _.getPlaybackStartPerf(),
|
|
828
|
+
playbackElapsedMs: b,
|
|
829
|
+
queueLength: A.length,
|
|
830
|
+
activeViseme: Mt(A, b),
|
|
831
|
+
segments: o.map((ne) => ({
|
|
832
|
+
...ne,
|
|
833
|
+
visemes: [...ne.visemes]
|
|
841
834
|
}))
|
|
842
835
|
});
|
|
843
|
-
},
|
|
844
|
-
n.onLipsyncDebug && (
|
|
845
|
-
|
|
846
|
-
const
|
|
847
|
-
|
|
836
|
+
}, k = (B, S) => {
|
|
837
|
+
n.onLipsyncDebug && (E = { event: B, spokenText: S }, g === 0 && (g = requestAnimationFrame(() => {
|
|
838
|
+
g = 0;
|
|
839
|
+
const b = E;
|
|
840
|
+
E = null, b && p(b.event, b.spokenText);
|
|
848
841
|
})));
|
|
849
|
-
},
|
|
842
|
+
}, x = (B, S, b, A, ne) => {
|
|
850
843
|
if (!n.onLipsyncDebug) return;
|
|
851
|
-
const
|
|
852
|
-
(
|
|
844
|
+
const M = s.slice(S), Y = b.filter(
|
|
845
|
+
(X) => String(X.symbol ?? X.viseme ?? "").trim()
|
|
853
846
|
);
|
|
854
847
|
o.push({
|
|
855
|
-
spokenText:
|
|
856
|
-
audioOffsetMs:
|
|
857
|
-
isNewSegment:
|
|
858
|
-
chunkDurationMs:
|
|
848
|
+
spokenText: B,
|
|
849
|
+
audioOffsetMs: M[0]?.vtime ?? 0,
|
|
850
|
+
isNewSegment: A,
|
|
851
|
+
chunkDurationMs: ne,
|
|
859
852
|
receivedAtMs: performance.now(),
|
|
860
|
-
visemes:
|
|
861
|
-
const
|
|
853
|
+
visemes: M.map((X, ae) => {
|
|
854
|
+
const Z = Y[ae];
|
|
862
855
|
return {
|
|
863
|
-
rawSymbol: String(
|
|
864
|
-
viseme:
|
|
865
|
-
startSec: Number(
|
|
866
|
-
durationSec: Number(
|
|
867
|
-
vtimeMs:
|
|
868
|
-
vdurationMs:
|
|
856
|
+
rawSymbol: String(Z?.symbol ?? Z?.viseme ?? X.viseme).trim(),
|
|
857
|
+
viseme: X.viseme,
|
|
858
|
+
startSec: Number(Z?.start ?? 0),
|
|
859
|
+
durationSec: Number(Z?.duration ?? 0),
|
|
860
|
+
vtimeMs: X.vtime,
|
|
861
|
+
vdurationMs: X.vduration
|
|
869
862
|
};
|
|
870
863
|
})
|
|
871
864
|
});
|
|
872
|
-
},
|
|
873
|
-
|
|
865
|
+
}, R = () => {
|
|
866
|
+
_.stop(), s.length = 0, i.length = 0, a.length = 0, f = "neutral", o.length = 0, d = "", e("idle"), k("reset"), h();
|
|
874
867
|
};
|
|
875
868
|
return {
|
|
876
|
-
setDeveloperToken: (
|
|
877
|
-
c =
|
|
869
|
+
setDeveloperToken: (B) => {
|
|
870
|
+
c = B;
|
|
878
871
|
},
|
|
879
|
-
setTtsEngineId: (
|
|
880
|
-
u =
|
|
872
|
+
setTtsEngineId: (B) => {
|
|
873
|
+
u = B;
|
|
881
874
|
},
|
|
882
875
|
getTtsEngineId: () => u,
|
|
883
|
-
speak: async (
|
|
884
|
-
|
|
885
|
-
const
|
|
886
|
-
if (!
|
|
876
|
+
speak: async (B, S) => {
|
|
877
|
+
R(), e("loading"), d = B, o.length = 0;
|
|
878
|
+
const b = c.trim();
|
|
879
|
+
if (!b)
|
|
887
880
|
throw new Error("Developer token required for avatar_ttsWithPoses");
|
|
888
|
-
const
|
|
889
|
-
|
|
890
|
-
const
|
|
881
|
+
const A = S?.ttsEngineId ?? u ?? Ye;
|
|
882
|
+
_.resetForNewStream(A), _.setStreamTtsEngineId(A);
|
|
883
|
+
const ne = S?.voiceId ?? er, M = S?.speakingRate ?? Dt, Y = Math.max(
|
|
891
884
|
Zt,
|
|
892
|
-
Math.min(en,
|
|
893
|
-
),
|
|
894
|
-
user_query:
|
|
895
|
-
ttsEngineId:
|
|
896
|
-
speakingRate:
|
|
885
|
+
Math.min(en, M)
|
|
886
|
+
), X = {
|
|
887
|
+
user_query: B,
|
|
888
|
+
ttsEngineId: A,
|
|
889
|
+
speakingRate: Y,
|
|
897
890
|
tenant: "aiTwin"
|
|
898
891
|
};
|
|
899
|
-
|
|
892
|
+
qn.has(A) && (X.voice_id = ne);
|
|
900
893
|
try {
|
|
901
|
-
const
|
|
894
|
+
const ae = await fetch(r, {
|
|
902
895
|
method: "POST",
|
|
903
896
|
headers: {
|
|
904
897
|
"Content-Type": "application/json",
|
|
905
|
-
Authorization: `Bearer ${
|
|
898
|
+
Authorization: `Bearer ${b}`
|
|
906
899
|
},
|
|
907
|
-
body: JSON.stringify(
|
|
900
|
+
body: JSON.stringify(X)
|
|
908
901
|
});
|
|
909
|
-
if (!
|
|
910
|
-
throw new Error(`avatar_ttsWithPoses failed (${
|
|
911
|
-
const
|
|
912
|
-
if (!
|
|
913
|
-
const
|
|
914
|
-
let
|
|
915
|
-
const
|
|
916
|
-
const
|
|
917
|
-
if (
|
|
918
|
-
if (
|
|
919
|
-
const
|
|
920
|
-
|
|
902
|
+
if (!ae.ok)
|
|
903
|
+
throw new Error(`avatar_ttsWithPoses failed (${ae.status})`);
|
|
904
|
+
const Z = ae.body;
|
|
905
|
+
if (!Z) throw new Error("No response body");
|
|
906
|
+
const de = Z.getReader(), fe = new TextDecoder();
|
|
907
|
+
let me = "";
|
|
908
|
+
const J = async (he) => {
|
|
909
|
+
const G = Gn(he);
|
|
910
|
+
if (G) {
|
|
911
|
+
if (G.event === "audio") {
|
|
912
|
+
const ie = G.data.chunk, w = G.data.visemes ?? [], I = G.data.words ?? [], T = G.data.is_new_segment ?? !1, U = G.data.sample_rate, F = s.length;
|
|
913
|
+
ie ? (await _.playAudioChunk(
|
|
921
914
|
s,
|
|
922
915
|
i,
|
|
923
|
-
|
|
924
|
-
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
{ sampleRate:
|
|
928
|
-
),
|
|
929
|
-
|
|
930
|
-
|
|
931
|
-
|
|
932
|
-
|
|
933
|
-
Ts(
|
|
934
|
-
),
|
|
916
|
+
ie,
|
|
917
|
+
w,
|
|
918
|
+
I,
|
|
919
|
+
T,
|
|
920
|
+
{ sampleRate: U }
|
|
921
|
+
), x(
|
|
922
|
+
B,
|
|
923
|
+
F,
|
|
924
|
+
w,
|
|
925
|
+
T,
|
|
926
|
+
Ts(ie, U)
|
|
927
|
+
), k("audio_chunk", B)) : (w.length > 0 || I.length > 0) && (_.queueTimingsOnly(
|
|
935
928
|
s,
|
|
936
929
|
i,
|
|
937
|
-
|
|
938
|
-
|
|
939
|
-
|
|
940
|
-
|
|
941
|
-
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
|
|
945
|
-
R,
|
|
930
|
+
w,
|
|
931
|
+
I,
|
|
932
|
+
T
|
|
933
|
+
), x(
|
|
934
|
+
B,
|
|
935
|
+
F,
|
|
936
|
+
w,
|
|
937
|
+
T,
|
|
946
938
|
null
|
|
947
|
-
),
|
|
948
|
-
} else if (
|
|
949
|
-
const
|
|
950
|
-
typeof
|
|
951
|
-
const
|
|
952
|
-
if (Array.isArray(
|
|
939
|
+
), k("audio_chunk", B));
|
|
940
|
+
} else if (G.event === "metadata") {
|
|
941
|
+
const ie = G.data.mood;
|
|
942
|
+
typeof ie == "string" && ie.trim() && (f = ie.trim());
|
|
943
|
+
const w = G.data.sentence_emotions;
|
|
944
|
+
if (Array.isArray(w)) {
|
|
953
945
|
a.length = 0;
|
|
954
|
-
for (const
|
|
955
|
-
if (!
|
|
956
|
-
const
|
|
946
|
+
for (const I of w) {
|
|
947
|
+
if (!I || typeof I != "object") continue;
|
|
948
|
+
const T = I;
|
|
957
949
|
a.push({
|
|
958
|
-
sentence_index: Number(
|
|
959
|
-
text: String(
|
|
960
|
-
sentiment: typeof
|
|
961
|
-
emotion: String(
|
|
962
|
-
start_word: Number(
|
|
963
|
-
end_word: Number(
|
|
950
|
+
sentence_index: Number(T.sentence_index ?? 0),
|
|
951
|
+
text: String(T.text ?? ""),
|
|
952
|
+
sentiment: typeof T.sentiment == "string" ? T.sentiment : void 0,
|
|
953
|
+
emotion: String(T.emotion ?? f),
|
|
954
|
+
start_word: Number(T.start_word ?? 0),
|
|
955
|
+
end_word: Number(T.end_word ?? 0)
|
|
964
956
|
});
|
|
965
957
|
}
|
|
966
958
|
}
|
|
967
|
-
|
|
968
|
-
} else if (
|
|
959
|
+
h(), k("metadata", B);
|
|
960
|
+
} else if (G.event === "error")
|
|
969
961
|
throw new Error(
|
|
970
|
-
String(
|
|
962
|
+
String(G.data.message ?? "avatar_ttsWithPoses stream error")
|
|
971
963
|
);
|
|
972
964
|
}
|
|
973
965
|
};
|
|
974
966
|
for (; ; ) {
|
|
975
|
-
const { done:
|
|
976
|
-
|
|
977
|
-
const
|
|
967
|
+
const { done: he, value: G } = await de.read();
|
|
968
|
+
G && (me += fe.decode(G, { stream: !0 }));
|
|
969
|
+
const ie = me.split(`
|
|
978
970
|
|
|
979
971
|
`);
|
|
980
|
-
|
|
981
|
-
for (const
|
|
982
|
-
if (
|
|
983
|
-
|
|
972
|
+
me = ie.pop() ?? "";
|
|
973
|
+
for (const w of ie) await J(w);
|
|
974
|
+
if (he) {
|
|
975
|
+
me.trim() && await J(me.trim()), _.markStreamComplete(s), k("bot_stopped", B);
|
|
984
976
|
break;
|
|
985
977
|
}
|
|
986
978
|
}
|
|
987
|
-
} catch (
|
|
988
|
-
throw console.error("[avatarTtsLipsync]",
|
|
979
|
+
} catch (ae) {
|
|
980
|
+
throw console.error("[avatarTtsLipsync]", ae), R(), e("error"), ae;
|
|
989
981
|
}
|
|
990
982
|
},
|
|
991
|
-
stop:
|
|
983
|
+
stop: R,
|
|
992
984
|
getVisemeQueue: () => s,
|
|
993
985
|
getWordQueue: () => i,
|
|
994
986
|
getSentenceEmotions: () => a,
|
|
995
|
-
getStreamMood: () =>
|
|
996
|
-
getPlaybackElapsedMs: () =>
|
|
997
|
-
isSpeaking: () =>
|
|
998
|
-
isWarmingUp: () =>
|
|
999
|
-
releaseWarmupHold: () =>
|
|
1000
|
-
setLipsyncWarmupHold: (
|
|
1001
|
-
|
|
1002
|
-
},
|
|
1003
|
-
getVoiceStream: () =>
|
|
1004
|
-
setPlaybackSpeed: (
|
|
1005
|
-
|
|
1006
|
-
},
|
|
1007
|
-
getPlaybackSpeed: () =>
|
|
1008
|
-
subscribe: (
|
|
987
|
+
getStreamMood: () => f,
|
|
988
|
+
getPlaybackElapsedMs: () => _.getPlaybackElapsedMs(),
|
|
989
|
+
isSpeaking: () => _.isSpeaking(),
|
|
990
|
+
isWarmingUp: () => _.isWarmingUp(),
|
|
991
|
+
releaseWarmupHold: () => _.releaseWarmupHold(),
|
|
992
|
+
setLipsyncWarmupHold: (B, S) => {
|
|
993
|
+
S && (D = S), _.setLipsyncWarmupHoldEnabled(B);
|
|
994
|
+
},
|
|
995
|
+
getVoiceStream: () => _.getVoiceStream(),
|
|
996
|
+
setPlaybackSpeed: (B) => {
|
|
997
|
+
_.setPlaybackSpeed(B);
|
|
998
|
+
},
|
|
999
|
+
getPlaybackSpeed: () => _.getPlaybackSpeed(),
|
|
1000
|
+
subscribe: (B) => (m.add(B), () => m.delete(B))
|
|
1009
1001
|
};
|
|
1010
1002
|
}
|
|
1011
|
-
const
|
|
1012
|
-
class As extends
|
|
1003
|
+
const nr = 16e3, rr = 16e3;
|
|
1004
|
+
class As extends Tr {
|
|
1013
1005
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
1014
1006
|
async deserialize(t) {
|
|
1015
1007
|
try {
|
|
@@ -1021,7 +1013,7 @@ class As extends Er {
|
|
|
1021
1013
|
}
|
|
1022
1014
|
}
|
|
1023
1015
|
}
|
|
1024
|
-
class Is extends
|
|
1016
|
+
class Is extends Er {
|
|
1025
1017
|
constructor() {
|
|
1026
1018
|
super(
|
|
1027
1019
|
!0,
|
|
@@ -1029,42 +1021,42 @@ class Is extends br {
|
|
|
1029
1021
|
void 0,
|
|
1030
1022
|
void 0,
|
|
1031
1023
|
512,
|
|
1032
|
-
|
|
1033
|
-
|
|
1024
|
+
nr,
|
|
1025
|
+
rr
|
|
1034
1026
|
);
|
|
1035
1027
|
}
|
|
1036
1028
|
/** Pipecat protobuf bot audio is unused — playback comes from avatar_audio_chunk. */
|
|
1037
1029
|
bufferBotAudio(t, n) {
|
|
1038
1030
|
}
|
|
1039
1031
|
}
|
|
1040
|
-
const
|
|
1041
|
-
function
|
|
1042
|
-
return
|
|
1032
|
+
const Ps = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
1033
|
+
function Ms(e) {
|
|
1034
|
+
return Ps.test(e.trim());
|
|
1043
1035
|
}
|
|
1044
|
-
function
|
|
1036
|
+
function Ds(e) {
|
|
1045
1037
|
const t = e.replace(/\/$/, "");
|
|
1046
1038
|
return t.startsWith("https://") ? `wss://${t.slice(8)}` : t.startsWith("http://") ? `ws://${t.slice(7)}` : t;
|
|
1047
1039
|
}
|
|
1048
|
-
function
|
|
1040
|
+
function Rs(e) {
|
|
1049
1041
|
if (e.wsUrl?.trim()) return e.wsUrl.trim();
|
|
1050
1042
|
const t = e.authToken?.trim();
|
|
1051
1043
|
if (!t)
|
|
1052
1044
|
throw new Error(
|
|
1053
1045
|
"Voice connect requires authToken (same JWT as SSE Authorization Bearer)."
|
|
1054
1046
|
);
|
|
1055
|
-
const n = e.apiBase ??
|
|
1047
|
+
const n = e.apiBase ?? dt, r = new URL(`${Ds(n)}/ws/voice`);
|
|
1056
1048
|
r.searchParams.set("authToken", t), r.searchParams.set("tenant", "aiTwin");
|
|
1057
1049
|
const s = e.voiceId?.trim();
|
|
1058
|
-
s &&
|
|
1050
|
+
s && Ms(s) && r.searchParams.set("voiceId", s);
|
|
1059
1051
|
const i = e.personaId?.trim();
|
|
1060
1052
|
i && r.searchParams.set("personaId", i);
|
|
1061
|
-
const a = e.speakingRate ??
|
|
1053
|
+
const a = e.speakingRate ?? Dt;
|
|
1062
1054
|
return r.searchParams.set(
|
|
1063
1055
|
"speaking_rate",
|
|
1064
1056
|
String(Math.max(Zt, Math.min(en, a)))
|
|
1065
1057
|
), e.ttsStream === !1 ? r.searchParams.set("tts_stream", "false") : r.searchParams.set("tts_stream", "true"), r.toString();
|
|
1066
1058
|
}
|
|
1067
|
-
function
|
|
1059
|
+
function Nt(e, t) {
|
|
1068
1060
|
if (!Array.isArray(e)) return [];
|
|
1069
1061
|
const n = [];
|
|
1070
1062
|
for (const r of e)
|
|
@@ -1078,7 +1070,7 @@ function Lt(e, t) {
|
|
|
1078
1070
|
});
|
|
1079
1071
|
return n;
|
|
1080
1072
|
}
|
|
1081
|
-
function
|
|
1073
|
+
function Bs(e) {
|
|
1082
1074
|
if (!e || typeof e != "object") return null;
|
|
1083
1075
|
const t = e, r = (t.data && typeof t.data == "object" && !Array.isArray(t.data) ? t.data : null) || t;
|
|
1084
1076
|
return {
|
|
@@ -1086,68 +1078,68 @@ function xs(e) {
|
|
|
1086
1078
|
type: String(r.type ?? t.type ?? "server-message")
|
|
1087
1079
|
};
|
|
1088
1080
|
}
|
|
1089
|
-
function
|
|
1081
|
+
function Ot(e) {
|
|
1090
1082
|
return e.is_new_segment === !0 || Number(e.audio_offset_ms ?? -1) === 0 ? !0 : Number(e.chunk_index ?? -1) === 0;
|
|
1091
1083
|
}
|
|
1092
1084
|
function Cs(e) {
|
|
1093
1085
|
return e?.transport?._mediaManager?._wavStreamPlayer ?? null;
|
|
1094
1086
|
}
|
|
1095
|
-
function
|
|
1087
|
+
function xs(e, t = {}) {
|
|
1096
1088
|
const n = [], r = [], s = [], i = [];
|
|
1097
|
-
let a = "", o = "neutral", d =
|
|
1098
|
-
const
|
|
1099
|
-
let
|
|
1100
|
-
const
|
|
1101
|
-
let
|
|
1102
|
-
const
|
|
1103
|
-
|
|
1104
|
-
},
|
|
1105
|
-
let
|
|
1106
|
-
const
|
|
1089
|
+
let a = "", o = "neutral", d = Ze, f = !1, c = null, u = null, m = { ...t }, g = 0, E = null;
|
|
1090
|
+
const h = /* @__PURE__ */ new Set(), D = [];
|
|
1091
|
+
let _ = !1, P = null, p = !0, k = "default";
|
|
1092
|
+
const x = /* @__PURE__ */ new Set();
|
|
1093
|
+
let R = null, K = 0, B = !1, S = null;
|
|
1094
|
+
const b = () => {
|
|
1095
|
+
S != null && (clearTimeout(S), S = null);
|
|
1096
|
+
}, A = () => h.forEach((l) => l());
|
|
1097
|
+
let ne = () => !1;
|
|
1098
|
+
const M = Xn(
|
|
1107
1099
|
{
|
|
1108
1100
|
onSpeakingStart: () => e("speaking"),
|
|
1109
1101
|
onSpeakingDone: () => e("done"),
|
|
1110
|
-
onNotify:
|
|
1111
|
-
shouldHoldForWarmup: () =>
|
|
1102
|
+
onNotify: A,
|
|
1103
|
+
shouldHoldForWarmup: () => ne()
|
|
1112
1104
|
},
|
|
1113
1105
|
d
|
|
1114
|
-
),
|
|
1115
|
-
if (
|
|
1106
|
+
), Y = () => {
|
|
1107
|
+
if (P) return P;
|
|
1116
1108
|
const l = new MessageChannel();
|
|
1117
1109
|
return l.port1.onmessage = () => {
|
|
1118
|
-
const v =
|
|
1119
|
-
v !== void 0 &&
|
|
1120
|
-
},
|
|
1121
|
-
},
|
|
1122
|
-
|
|
1123
|
-
},
|
|
1124
|
-
if (!
|
|
1125
|
-
const
|
|
1126
|
-
|
|
1110
|
+
const v = D.shift();
|
|
1111
|
+
v !== void 0 && j(v), D.length > 0 ? l.port2.postMessage(null) : _ = !1;
|
|
1112
|
+
}, P = l, l;
|
|
1113
|
+
}, X = (l) => {
|
|
1114
|
+
D.push(l), !_ && (_ = !0, Y().port2.postMessage(null));
|
|
1115
|
+
}, ae = () => M.getPlaybackElapsedMs(), Z = (l, v = a) => {
|
|
1116
|
+
if (!m.onLipsyncDebug) return;
|
|
1117
|
+
const O = ae(), H = n;
|
|
1118
|
+
m.onLipsyncDebug({
|
|
1127
1119
|
event: l,
|
|
1128
1120
|
spokenText: v,
|
|
1129
1121
|
mood: o,
|
|
1130
|
-
playbackAnchorPerf:
|
|
1131
|
-
playbackElapsedMs:
|
|
1132
|
-
queueLength:
|
|
1133
|
-
activeViseme:
|
|
1134
|
-
segments: i.map((
|
|
1135
|
-
...
|
|
1136
|
-
visemes: [...
|
|
1122
|
+
playbackAnchorPerf: M.getPlaybackStartPerf(),
|
|
1123
|
+
playbackElapsedMs: O,
|
|
1124
|
+
queueLength: H.length,
|
|
1125
|
+
activeViseme: Mt(H, O),
|
|
1126
|
+
segments: i.map((oe) => ({
|
|
1127
|
+
...oe,
|
|
1128
|
+
visemes: [...oe.visemes]
|
|
1137
1129
|
}))
|
|
1138
1130
|
});
|
|
1139
|
-
},
|
|
1140
|
-
|
|
1141
|
-
|
|
1142
|
-
const
|
|
1143
|
-
|
|
1131
|
+
}, de = (l, v) => {
|
|
1132
|
+
m.onLipsyncDebug && (E = { event: l, spokenText: v }, g === 0 && (g = requestAnimationFrame(() => {
|
|
1133
|
+
g = 0;
|
|
1134
|
+
const O = E;
|
|
1135
|
+
E = null, O && Z(O.event, O.spokenText);
|
|
1144
1136
|
})));
|
|
1145
1137
|
}, fe = () => {
|
|
1146
|
-
|
|
1147
|
-
},
|
|
1138
|
+
p = !0, x.clear(), M.clearAborted();
|
|
1139
|
+
}, me = () => {
|
|
1148
1140
|
const l = Cs(c);
|
|
1149
1141
|
if (l) {
|
|
1150
|
-
|
|
1142
|
+
k = `bot-${Date.now()}`, l.interruptedTrackIds = { [k]: !0 };
|
|
1151
1143
|
try {
|
|
1152
1144
|
l.interrupt?.();
|
|
1153
1145
|
} catch {
|
|
@@ -1158,264 +1150,261 @@ function Bs(e, t = {}) {
|
|
|
1158
1150
|
v?.interrupt?.();
|
|
1159
1151
|
} catch {
|
|
1160
1152
|
}
|
|
1161
|
-
},
|
|
1153
|
+
}, J = (l) => {
|
|
1162
1154
|
const v = l.context_id?.trim();
|
|
1163
|
-
return v &&
|
|
1164
|
-
},
|
|
1165
|
-
|
|
1155
|
+
return v && x.has(v) ? !0 : p ? !1 : !(l.type === "avatar_metadata" || Ot(l));
|
|
1156
|
+
}, he = (l) => {
|
|
1157
|
+
p = !1;
|
|
1166
1158
|
const v = l.context_id?.trim();
|
|
1167
|
-
v &&
|
|
1168
|
-
},
|
|
1159
|
+
v && x.add(v), b(), B = !1, D.length = 0, _ = !1, R?.abort(), R = null, K += 1, me(), M.bargeIn(), G(), e("idle"), de("interrupt"), A();
|
|
1160
|
+
}, G = () => {
|
|
1169
1161
|
n.length = 0, r.length = 0, i.length = 0, a = "", o = "neutral", s.length = 0;
|
|
1170
|
-
},
|
|
1171
|
-
|
|
1172
|
-
},
|
|
1173
|
-
|
|
1174
|
-
},
|
|
1162
|
+
}, ie = () => {
|
|
1163
|
+
M.stop(), G(), de("reset"), A();
|
|
1164
|
+
}, w = () => {
|
|
1165
|
+
ie(), e("idle"), A();
|
|
1166
|
+
}, I = (l, v) => {
|
|
1175
1167
|
typeof l.mood == "string" && l.mood.trim() && (o = l.mood.trim()), Array.isArray(l.sentence_emotions) && l.sentence_emotions.length > 0 && (v && (s.length = 0), s.push(
|
|
1176
|
-
...
|
|
1168
|
+
...Nt(l.sentence_emotions, o)
|
|
1177
1169
|
));
|
|
1178
|
-
},
|
|
1179
|
-
if (
|
|
1170
|
+
}, T = (l) => {
|
|
1171
|
+
if (J({ ...l, type: "avatar_metadata" }))
|
|
1180
1172
|
return;
|
|
1181
|
-
fe(),
|
|
1173
|
+
fe(), B = !0;
|
|
1182
1174
|
const v = String(l.spoken_text ?? l.text ?? "").trim();
|
|
1183
|
-
v && (a = v),
|
|
1184
|
-
...
|
|
1185
|
-
), Array.isArray(l.gestures) && l.gestures,
|
|
1186
|
-
},
|
|
1187
|
-
if (!
|
|
1188
|
-
const
|
|
1189
|
-
(
|
|
1175
|
+
v && (a = v), M.resetForNewStream(d), typeof l.mood == "string" && l.mood.trim() && (o = l.mood.trim()), s.length = 0, s.push(
|
|
1176
|
+
...Nt(l.sentence_emotions, o)
|
|
1177
|
+
), Array.isArray(l.gestures) && l.gestures, de("metadata", v), A();
|
|
1178
|
+
}, U = (l, v, O, H) => {
|
|
1179
|
+
if (!m.onLipsyncDebug) return;
|
|
1180
|
+
const oe = n.slice(O), Be = H.filter(
|
|
1181
|
+
(ce) => String(ce.symbol ?? ce.viseme ?? "").trim()
|
|
1190
1182
|
);
|
|
1191
1183
|
i.push({
|
|
1192
1184
|
spokenText: v,
|
|
1193
|
-
audioOffsetMs:
|
|
1185
|
+
audioOffsetMs: oe[0]?.vtime ?? 0,
|
|
1194
1186
|
isNewSegment: !!l.is_new_segment,
|
|
1195
1187
|
chunkDurationMs: l.chunk_duration_ms != null ? Number(l.chunk_duration_ms) : null,
|
|
1196
1188
|
receivedAtMs: performance.now(),
|
|
1197
|
-
visemes:
|
|
1198
|
-
const
|
|
1189
|
+
visemes: oe.map((ce, Ce) => {
|
|
1190
|
+
const ge = Be[Ce];
|
|
1199
1191
|
return {
|
|
1200
|
-
rawSymbol: String(
|
|
1201
|
-
viseme:
|
|
1202
|
-
startSec: Number(
|
|
1203
|
-
durationSec: Number(
|
|
1204
|
-
vtimeMs:
|
|
1205
|
-
vdurationMs:
|
|
1192
|
+
rawSymbol: String(ge?.symbol ?? ge?.viseme ?? ce.viseme).trim(),
|
|
1193
|
+
viseme: ce.viseme,
|
|
1194
|
+
startSec: Number(ge?.start ?? 0),
|
|
1195
|
+
durationSec: Number(ge?.duration ?? 0),
|
|
1196
|
+
vtimeMs: ce.vtime,
|
|
1197
|
+
vdurationMs: ce.vduration
|
|
1206
1198
|
};
|
|
1207
1199
|
})
|
|
1208
1200
|
});
|
|
1209
|
-
},
|
|
1210
|
-
if (
|
|
1211
|
-
|
|
1212
|
-
const v = String(l.spoken_text ?? l.text ?? "").trim(),
|
|
1213
|
-
|
|
1201
|
+
}, F = (l) => {
|
|
1202
|
+
if (J(l)) return;
|
|
1203
|
+
b(), Ot(l) && fe();
|
|
1204
|
+
const v = String(l.spoken_text ?? l.text ?? "").trim(), O = Ot(l), H = l.visemes ?? [], oe = l.words ?? [], Be = String(l.chunk ?? "").trim(), ce = B;
|
|
1205
|
+
ce && (B = !1), v && (a = v), I(l, O), ce ? M.resetForNewStream(d) : O && M.resumeBotStream();
|
|
1214
1206
|
const Ce = n.length;
|
|
1215
|
-
|
|
1207
|
+
M.playAudioChunk(
|
|
1216
1208
|
n,
|
|
1217
1209
|
r,
|
|
1218
|
-
|
|
1219
|
-
|
|
1220
|
-
|
|
1221
|
-
|
|
1210
|
+
Be,
|
|
1211
|
+
H,
|
|
1212
|
+
oe,
|
|
1213
|
+
O,
|
|
1222
1214
|
{
|
|
1223
1215
|
sampleRate: l.sample_rate,
|
|
1224
|
-
newStream:
|
|
1225
|
-
audioOffsetMs: l.audio_offset_ms != null ? Number(l.audio_offset_ms) : void 0,
|
|
1216
|
+
newStream: ce,
|
|
1226
1217
|
onNewStream: () => {
|
|
1227
1218
|
i.length = 0;
|
|
1228
1219
|
}
|
|
1229
1220
|
}
|
|
1230
1221
|
).then(() => {
|
|
1231
|
-
|
|
1222
|
+
U(l, v, Ce, H), de("audio_chunk", v);
|
|
1232
1223
|
});
|
|
1233
|
-
},
|
|
1234
|
-
if (
|
|
1224
|
+
}, te = (l) => {
|
|
1225
|
+
if (J(l)) return;
|
|
1235
1226
|
(l.is_new_segment || Number(l.audio_offset_ms ?? -1) === 0) && fe(), console.warn(
|
|
1236
1227
|
"[realtimeVoice] avatar_lipsync is deprecated — expect avatar_audio_chunk"
|
|
1237
1228
|
);
|
|
1238
1229
|
const v = String(l.spoken_text ?? l.text ?? "").trim();
|
|
1239
|
-
v && (a = v),
|
|
1240
|
-
const
|
|
1241
|
-
|
|
1230
|
+
v && (a = v), I(l, !!l.is_new_segment);
|
|
1231
|
+
const O = n.length;
|
|
1232
|
+
M.queueTimingsOnly(
|
|
1242
1233
|
n,
|
|
1243
1234
|
r,
|
|
1244
1235
|
l.visemes ?? [],
|
|
1245
1236
|
l.words ?? [],
|
|
1246
|
-
!!l.is_new_segment
|
|
1247
|
-
|
|
1248
|
-
), T(
|
|
1237
|
+
!!l.is_new_segment
|
|
1238
|
+
), U(
|
|
1249
1239
|
l,
|
|
1250
1240
|
v,
|
|
1251
|
-
|
|
1241
|
+
O,
|
|
1252
1242
|
l.visemes ?? []
|
|
1253
|
-
),
|
|
1254
|
-
},
|
|
1243
|
+
), de("lipsync", v), A();
|
|
1244
|
+
}, ee = async (l) => {
|
|
1255
1245
|
const v = String(l.text ?? "").trim();
|
|
1256
1246
|
if (!v) return;
|
|
1257
|
-
const
|
|
1258
|
-
if (!
|
|
1247
|
+
const O = m.authToken?.trim();
|
|
1248
|
+
if (!O) {
|
|
1259
1249
|
console.error("[realtimeVoice] avatar_speak requires authToken");
|
|
1260
1250
|
return;
|
|
1261
1251
|
}
|
|
1262
|
-
|
|
1263
|
-
const
|
|
1264
|
-
|
|
1265
|
-
const
|
|
1266
|
-
fe(),
|
|
1267
|
-
const
|
|
1252
|
+
R?.abort();
|
|
1253
|
+
const H = new AbortController();
|
|
1254
|
+
R = H;
|
|
1255
|
+
const oe = ++K;
|
|
1256
|
+
fe(), M.resetForNewStream(d), a = v;
|
|
1257
|
+
const ce = `${(m.apiBase ?? dt).replace(/\/$/, "")}/avatar_ttsWithPoses`, Ce = m.voiceId?.trim() || tr, ge = m.speakingRate ?? Dt, tt = Math.max(
|
|
1268
1258
|
Zt,
|
|
1269
|
-
Math.min(en,
|
|
1270
|
-
),
|
|
1259
|
+
Math.min(en, ge)
|
|
1260
|
+
), nt = {
|
|
1271
1261
|
user_query: v,
|
|
1272
1262
|
ttsEngineId: d,
|
|
1273
|
-
speakingRate:
|
|
1263
|
+
speakingRate: tt,
|
|
1274
1264
|
tenant: "aiTwin"
|
|
1275
1265
|
};
|
|
1276
|
-
|
|
1266
|
+
qn.has(d) && (nt.voice_id = Ce);
|
|
1277
1267
|
try {
|
|
1278
|
-
const se = await fetch(
|
|
1268
|
+
const se = await fetch(ce, {
|
|
1279
1269
|
method: "POST",
|
|
1280
1270
|
headers: {
|
|
1281
1271
|
"Content-Type": "application/json",
|
|
1282
|
-
Authorization: `Bearer ${
|
|
1272
|
+
Authorization: `Bearer ${O}`
|
|
1283
1273
|
},
|
|
1284
|
-
body: JSON.stringify(
|
|
1285
|
-
signal:
|
|
1274
|
+
body: JSON.stringify(nt),
|
|
1275
|
+
signal: H.signal
|
|
1286
1276
|
});
|
|
1287
1277
|
if (!se.ok)
|
|
1288
1278
|
throw new Error(`avatar_ttsWithPoses failed (${se.status})`);
|
|
1289
|
-
const
|
|
1290
|
-
if (!
|
|
1291
|
-
const mt =
|
|
1279
|
+
const rt = se.body;
|
|
1280
|
+
if (!rt) throw new Error("No response body");
|
|
1281
|
+
const mt = rt.getReader(), ht = new TextDecoder();
|
|
1292
1282
|
let be = "";
|
|
1293
|
-
const
|
|
1294
|
-
if (
|
|
1283
|
+
const st = async (Ee) => {
|
|
1284
|
+
if (oe !== K || H.signal.aborted || !p)
|
|
1295
1285
|
return;
|
|
1296
|
-
const
|
|
1297
|
-
if (
|
|
1298
|
-
if (
|
|
1299
|
-
const le =
|
|
1300
|
-
le ? await
|
|
1286
|
+
const ue = Gn(Ee);
|
|
1287
|
+
if (ue) {
|
|
1288
|
+
if (ue.event === "audio") {
|
|
1289
|
+
const le = ue.data.chunk, pe = ue.data.visemes ?? [], z = ue.data.words ?? [], Q = ue.data.is_new_segment ?? !1, pt = ue.data.sample_rate;
|
|
1290
|
+
le ? await M.playAudioChunk(
|
|
1301
1291
|
n,
|
|
1302
1292
|
r,
|
|
1303
1293
|
le,
|
|
1304
1294
|
pe,
|
|
1305
|
-
|
|
1306
|
-
|
|
1307
|
-
{ sampleRate: pt
|
|
1308
|
-
) : (pe.length > 0 ||
|
|
1295
|
+
z,
|
|
1296
|
+
Q,
|
|
1297
|
+
{ sampleRate: pt }
|
|
1298
|
+
) : (pe.length > 0 || z.length > 0) && M.queueTimingsOnly(
|
|
1309
1299
|
n,
|
|
1310
1300
|
r,
|
|
1311
1301
|
pe,
|
|
1312
|
-
|
|
1313
|
-
|
|
1314
|
-
we
|
|
1302
|
+
z,
|
|
1303
|
+
Q
|
|
1315
1304
|
);
|
|
1316
|
-
} else if (
|
|
1317
|
-
const le =
|
|
1305
|
+
} else if (ue.event === "metadata") {
|
|
1306
|
+
const le = ue.data.mood;
|
|
1318
1307
|
typeof le == "string" && le.trim() && (o = le.trim());
|
|
1319
|
-
const pe =
|
|
1308
|
+
const pe = ue.data.sentence_emotions;
|
|
1320
1309
|
Array.isArray(pe) && (s.length = 0, s.push(
|
|
1321
|
-
...
|
|
1322
|
-
)),
|
|
1323
|
-
} else if (
|
|
1310
|
+
...Nt(pe, o)
|
|
1311
|
+
)), A();
|
|
1312
|
+
} else if (ue.event === "error")
|
|
1324
1313
|
throw new Error(
|
|
1325
|
-
String(
|
|
1314
|
+
String(ue.data.message ?? "avatar_ttsWithPoses stream error")
|
|
1326
1315
|
);
|
|
1327
1316
|
}
|
|
1328
1317
|
};
|
|
1329
|
-
for (; !(
|
|
1330
|
-
const { done: Ee, value:
|
|
1331
|
-
|
|
1318
|
+
for (; !(oe !== K || H.signal.aborted || !p); ) {
|
|
1319
|
+
const { done: Ee, value: ue } = await mt.read();
|
|
1320
|
+
ue && (be += ht.decode(ue, { stream: !0 }));
|
|
1332
1321
|
const le = be.split(`
|
|
1333
1322
|
|
|
1334
1323
|
`);
|
|
1335
1324
|
be = le.pop() ?? "";
|
|
1336
|
-
for (const pe of le) await
|
|
1325
|
+
for (const pe of le) await st(pe);
|
|
1337
1326
|
if (Ee) {
|
|
1338
|
-
be.trim() && await
|
|
1327
|
+
be.trim() && await st(be.trim()), oe === K && !H.signal.aborted && p && M.markStreamComplete(n);
|
|
1339
1328
|
break;
|
|
1340
1329
|
}
|
|
1341
1330
|
}
|
|
1342
1331
|
} catch (se) {
|
|
1343
|
-
if (
|
|
1344
|
-
console.error("[realtimeVoice] avatar_speak failed:", se), e("error"),
|
|
1332
|
+
if (H.signal.aborted || !p) return;
|
|
1333
|
+
console.error("[realtimeVoice] avatar_speak failed:", se), e("error"), A();
|
|
1345
1334
|
} finally {
|
|
1346
|
-
|
|
1335
|
+
R === H && (R = null);
|
|
1347
1336
|
}
|
|
1348
|
-
},
|
|
1349
|
-
const v =
|
|
1337
|
+
}, j = (l) => {
|
|
1338
|
+
const v = Bs(l);
|
|
1350
1339
|
if (!v) {
|
|
1351
1340
|
console.warn("[realtimeVoice] server message with no payload", l);
|
|
1352
1341
|
return;
|
|
1353
1342
|
}
|
|
1354
|
-
const
|
|
1355
|
-
switch (
|
|
1343
|
+
const O = String(v.type ?? "unknown");
|
|
1344
|
+
switch (O !== "avatar_metadata" && O !== "avatar_audio_chunk" && O !== "avatar_lipsync" && O !== "avatar_interrupt" && O !== "error" && console.debug("[realtimeVoice] server message", O, v), O) {
|
|
1356
1345
|
case "avatar_metadata":
|
|
1357
|
-
|
|
1346
|
+
T(v);
|
|
1358
1347
|
break;
|
|
1359
1348
|
case "avatar_audio_chunk":
|
|
1360
|
-
|
|
1349
|
+
F(v);
|
|
1361
1350
|
break;
|
|
1362
1351
|
case "avatar_lipsync":
|
|
1363
|
-
|
|
1352
|
+
te(v);
|
|
1364
1353
|
break;
|
|
1365
1354
|
case "avatar_interrupt":
|
|
1366
|
-
|
|
1355
|
+
he(v);
|
|
1367
1356
|
break;
|
|
1368
1357
|
case "error": {
|
|
1369
|
-
const
|
|
1370
|
-
console.error("[realtimeVoice] server error:",
|
|
1358
|
+
const H = String(v.message ?? "Voice session error");
|
|
1359
|
+
console.error("[realtimeVoice] server error:", H), e("error"), A();
|
|
1371
1360
|
break;
|
|
1372
1361
|
}
|
|
1373
1362
|
case "avatar_speak":
|
|
1374
|
-
|
|
1363
|
+
ee(v);
|
|
1375
1364
|
break;
|
|
1376
1365
|
}
|
|
1377
|
-
},
|
|
1378
|
-
transport: new
|
|
1366
|
+
}, q = () => c || (u = new Is(), c = new kr({
|
|
1367
|
+
transport: new br({
|
|
1379
1368
|
mediaManager: u,
|
|
1380
1369
|
serializer: new As(),
|
|
1381
|
-
recorderSampleRate:
|
|
1382
|
-
playerSampleRate:
|
|
1370
|
+
recorderSampleRate: nr,
|
|
1371
|
+
playerSampleRate: rr
|
|
1383
1372
|
}),
|
|
1384
1373
|
enableCam: !1,
|
|
1385
1374
|
enableMic: !0,
|
|
1386
1375
|
callbacks: {
|
|
1387
1376
|
onBotReady: () => {
|
|
1388
|
-
|
|
1377
|
+
f = !0, e("idle"), A();
|
|
1389
1378
|
},
|
|
1390
1379
|
onDisconnected: () => {
|
|
1391
|
-
|
|
1380
|
+
f = !1, w();
|
|
1392
1381
|
},
|
|
1393
1382
|
onError: (l) => {
|
|
1394
1383
|
const v = typeof l == "object" && l !== null && "data" in l ? String(l.data ?? l) : String(l);
|
|
1395
|
-
console.error("[realtimeVoice]", v, l), e("error"),
|
|
1384
|
+
console.error("[realtimeVoice]", v, l), e("error"), A();
|
|
1396
1385
|
},
|
|
1397
1386
|
onTransportStateChanged: (l) => {
|
|
1398
|
-
l === "error" && (e("error"),
|
|
1387
|
+
l === "error" && (e("error"), A());
|
|
1399
1388
|
},
|
|
1400
1389
|
onServerMessage: (l) => {
|
|
1401
|
-
|
|
1390
|
+
X(l);
|
|
1402
1391
|
},
|
|
1403
1392
|
onUserStartedSpeaking: () => {
|
|
1404
|
-
|
|
1393
|
+
he({});
|
|
1405
1394
|
},
|
|
1406
1395
|
onBotStartedSpeaking: () => {
|
|
1407
|
-
fe(),
|
|
1396
|
+
fe(), de("bot_started");
|
|
1408
1397
|
},
|
|
1409
1398
|
onBotStoppedSpeaking: () => {
|
|
1410
|
-
|
|
1411
|
-
|
|
1399
|
+
p && (b(), S = setTimeout(() => {
|
|
1400
|
+
S = null, p && (M.markStreamComplete(n), de("bot_stopped"));
|
|
1412
1401
|
}, 450));
|
|
1413
1402
|
},
|
|
1414
1403
|
onUserTranscript: (l) => {
|
|
1415
|
-
|
|
1404
|
+
m.onUserTranscript?.(l.text, !!l.final);
|
|
1416
1405
|
},
|
|
1417
1406
|
onBotOutput: (l) => {
|
|
1418
|
-
|
|
1407
|
+
m.onBotOutput?.(l.text);
|
|
1419
1408
|
}
|
|
1420
1409
|
}
|
|
1421
1410
|
}), c);
|
|
@@ -1423,71 +1412,71 @@ function Bs(e, t = {}) {
|
|
|
1423
1412
|
setDeveloperToken: (l) => {
|
|
1424
1413
|
},
|
|
1425
1414
|
setTtsEngineId: (l) => {
|
|
1426
|
-
d = l,
|
|
1415
|
+
d = l, M.setStreamTtsEngineId(l);
|
|
1427
1416
|
},
|
|
1428
1417
|
getTtsEngineId: () => d,
|
|
1429
1418
|
speak: async (l, v) => {
|
|
1430
|
-
const
|
|
1431
|
-
if (
|
|
1432
|
-
if (!c || !
|
|
1419
|
+
const O = l.trim();
|
|
1420
|
+
if (O) {
|
|
1421
|
+
if (!c || !f)
|
|
1433
1422
|
throw new Error(
|
|
1434
1423
|
"Realtime voice is not connected. Call connect() first."
|
|
1435
1424
|
);
|
|
1436
|
-
|
|
1425
|
+
ie(), await c.sendText(O);
|
|
1437
1426
|
}
|
|
1438
1427
|
},
|
|
1439
1428
|
stop: () => {
|
|
1440
|
-
|
|
1429
|
+
R?.abort(), R = null, K += 1, fe(), ie(), e("idle"), A();
|
|
1441
1430
|
},
|
|
1442
1431
|
connect: async (l) => {
|
|
1443
|
-
if (l && (
|
|
1432
|
+
if (l && (m = { ...m, ...l }), !m.authToken?.trim())
|
|
1444
1433
|
throw new Error(
|
|
1445
1434
|
"Voice connect requires authToken (same JWT as SSE Authorization Bearer)."
|
|
1446
1435
|
);
|
|
1447
1436
|
e("loading");
|
|
1448
|
-
const v =
|
|
1437
|
+
const v = q();
|
|
1449
1438
|
await v.initDevices();
|
|
1450
|
-
const
|
|
1451
|
-
console.info("[realtimeVoice] connecting (avatar_audio_chunk RTVI):",
|
|
1439
|
+
const O = Rs(m);
|
|
1440
|
+
console.info("[realtimeVoice] connecting (avatar_audio_chunk RTVI):", O);
|
|
1452
1441
|
try {
|
|
1453
|
-
await v.connect({ wsUrl:
|
|
1454
|
-
} catch (
|
|
1455
|
-
|
|
1456
|
-
const
|
|
1457
|
-
throw new Error(`${
|
|
1442
|
+
await v.connect({ wsUrl: O });
|
|
1443
|
+
} catch (H) {
|
|
1444
|
+
f = !1, e("error"), A();
|
|
1445
|
+
const oe = H instanceof Error ? H.message : "Realtime voice connect failed (WebSocket 101 only means upgrade OK — check authToken/origin/RTVI handshake)";
|
|
1446
|
+
throw new Error(`${oe} — ${O}`);
|
|
1458
1447
|
}
|
|
1459
|
-
|
|
1448
|
+
f = !0, e("idle"), A();
|
|
1460
1449
|
},
|
|
1461
1450
|
disconnect: async () => {
|
|
1462
|
-
if (
|
|
1451
|
+
if (b(), B = !1, D.length = 0, _ = !1, R?.abort(), R = null, K += 1, fe(), c)
|
|
1463
1452
|
try {
|
|
1464
1453
|
await c.disconnect();
|
|
1465
1454
|
} catch (l) {
|
|
1466
1455
|
console.error("[realtimeVoice] disconnect failed:", l);
|
|
1467
1456
|
}
|
|
1468
|
-
|
|
1457
|
+
f = !1, w();
|
|
1469
1458
|
},
|
|
1470
|
-
isConnected: () =>
|
|
1459
|
+
isConnected: () => f,
|
|
1471
1460
|
unlockAudio: async () => {
|
|
1472
|
-
await
|
|
1461
|
+
await M.primeAudioContext();
|
|
1473
1462
|
},
|
|
1474
1463
|
getVisemeQueue: () => n,
|
|
1475
1464
|
getWordQueue: () => r,
|
|
1476
1465
|
getSentenceEmotions: () => s,
|
|
1477
1466
|
getStreamMood: () => o,
|
|
1478
|
-
getPlaybackElapsedMs:
|
|
1479
|
-
isSpeaking: () =>
|
|
1480
|
-
isWarmingUp: () =>
|
|
1481
|
-
releaseWarmupHold: () =>
|
|
1467
|
+
getPlaybackElapsedMs: ae,
|
|
1468
|
+
isSpeaking: () => M.isSpeaking(),
|
|
1469
|
+
isWarmingUp: () => M.isWarmingUp(),
|
|
1470
|
+
releaseWarmupHold: () => M.releaseWarmupHold(),
|
|
1482
1471
|
setLipsyncWarmupHold: (l, v) => {
|
|
1483
|
-
v && (
|
|
1472
|
+
v && (ne = v), M.setLipsyncWarmupHoldEnabled(l);
|
|
1484
1473
|
},
|
|
1485
|
-
getVoiceStream: () =>
|
|
1474
|
+
getVoiceStream: () => M.getVoiceStream(),
|
|
1486
1475
|
setPlaybackSpeed: (l) => {
|
|
1487
|
-
|
|
1476
|
+
M.setPlaybackSpeed(l);
|
|
1488
1477
|
},
|
|
1489
|
-
getPlaybackSpeed: () =>
|
|
1490
|
-
subscribe: (l) => (
|
|
1478
|
+
getPlaybackSpeed: () => M.getPlaybackSpeed(),
|
|
1479
|
+
subscribe: (l) => (h.add(l), () => h.delete(l))
|
|
1491
1480
|
};
|
|
1492
1481
|
}
|
|
1493
1482
|
function Fs(e, t, n) {
|
|
@@ -1496,7 +1485,7 @@ function Fs(e, t, n) {
|
|
|
1496
1485
|
height: e.crop?.source_height ?? n
|
|
1497
1486
|
};
|
|
1498
1487
|
}
|
|
1499
|
-
function
|
|
1488
|
+
function Ls(e, t) {
|
|
1500
1489
|
const n = e.crop;
|
|
1501
1490
|
return {
|
|
1502
1491
|
x: t?.source_x ?? n?.x ?? 0,
|
|
@@ -1505,18 +1494,18 @@ function Os(e, t) {
|
|
|
1505
1494
|
height: t?.source_h ?? n?.height ?? e.frame_height ?? 0
|
|
1506
1495
|
};
|
|
1507
1496
|
}
|
|
1508
|
-
function
|
|
1497
|
+
function Ns(e) {
|
|
1509
1498
|
return e ? (e.w ?? 0) > 0 && (e.h ?? 0) > 0 : !1;
|
|
1510
1499
|
}
|
|
1511
|
-
async function
|
|
1500
|
+
async function Rt(e, t) {
|
|
1512
1501
|
const n = await fetch(e);
|
|
1513
1502
|
if (!n.ok) throw new Error(`Failed to load encrypted asset: ${e}`);
|
|
1514
1503
|
const r = await n.arrayBuffer();
|
|
1515
|
-
return
|
|
1504
|
+
return zr(r, t);
|
|
1516
1505
|
}
|
|
1517
|
-
async function
|
|
1506
|
+
async function Os(e, t) {
|
|
1518
1507
|
if (!t) throw new Error("Missing asset key for encrypted JSON");
|
|
1519
|
-
const n = await
|
|
1508
|
+
const n = await Rt(e, t), r = new TextDecoder().decode(n);
|
|
1520
1509
|
return JSON.parse(r);
|
|
1521
1510
|
}
|
|
1522
1511
|
async function Us(e) {
|
|
@@ -1546,21 +1535,21 @@ function Ws(e) {
|
|
|
1546
1535
|
return URL.createObjectURL(t);
|
|
1547
1536
|
}
|
|
1548
1537
|
async function Hs(e) {
|
|
1549
|
-
const t =
|
|
1550
|
-
if (!
|
|
1538
|
+
const t = Zr();
|
|
1539
|
+
if (!Pt()) return t;
|
|
1551
1540
|
if (!e) throw new Error("Missing asset key for encrypted idle video");
|
|
1552
|
-
const n = await
|
|
1541
|
+
const n = await Rt(t, e);
|
|
1553
1542
|
return Ws(n);
|
|
1554
1543
|
}
|
|
1555
1544
|
function tn(e, t) {
|
|
1556
1545
|
return `${e}/${t}_minus_sil.png`;
|
|
1557
1546
|
}
|
|
1558
|
-
const
|
|
1547
|
+
const sr = 5;
|
|
1559
1548
|
function nn(e) {
|
|
1560
1549
|
const t = e?.composite_threshold;
|
|
1561
1550
|
if (typeof t == "number" && t > 0) return t;
|
|
1562
1551
|
const n = e?.crop?.content_threshold;
|
|
1563
|
-
return typeof n == "number" && n > 0 ? n :
|
|
1552
|
+
return typeof n == "number" && n > 0 ? n : sr;
|
|
1564
1553
|
}
|
|
1565
1554
|
const ta = [
|
|
1566
1555
|
"aa",
|
|
@@ -1581,7 +1570,7 @@ const ta = [
|
|
|
1581
1570
|
"t01_0.25",
|
|
1582
1571
|
"t02_0.50",
|
|
1583
1572
|
"t03_0.75"
|
|
1584
|
-
], $s = $t.length,
|
|
1573
|
+
], $s = $t.length, Pn = /* @__PURE__ */ new Set([
|
|
1585
1574
|
"aa__kk",
|
|
1586
1575
|
"aa__nn",
|
|
1587
1576
|
"aa__sil",
|
|
@@ -1691,13 +1680,13 @@ const ta = [
|
|
|
1691
1680
|
function Mn(e, t) {
|
|
1692
1681
|
return `${e}__${t}`;
|
|
1693
1682
|
}
|
|
1694
|
-
function
|
|
1683
|
+
function Dn(e, t) {
|
|
1695
1684
|
return `pairs/${e}/${t}_minus_sil.png`;
|
|
1696
1685
|
}
|
|
1697
1686
|
function Et(e) {
|
|
1698
1687
|
return `${e}_minus_sil.png`;
|
|
1699
1688
|
}
|
|
1700
|
-
function
|
|
1689
|
+
function ir(e, t) {
|
|
1701
1690
|
if (t.has(e)) return e;
|
|
1702
1691
|
const n = /^pairs\/([^/]+)\//.exec(e);
|
|
1703
1692
|
if (!n) return null;
|
|
@@ -1706,25 +1695,25 @@ function sr(e, t) {
|
|
|
1706
1695
|
const s = Et(r);
|
|
1707
1696
|
return t.has(s) ? s : null;
|
|
1708
1697
|
}
|
|
1709
|
-
function
|
|
1698
|
+
function ar(e, t) {
|
|
1710
1699
|
return e.filter((n) => t.has(n));
|
|
1711
1700
|
}
|
|
1712
1701
|
function qs(e, t, n) {
|
|
1713
1702
|
const r = rn(e, t);
|
|
1714
|
-
return
|
|
1703
|
+
return ar(r, n).length > 0;
|
|
1715
1704
|
}
|
|
1716
1705
|
function rn(e, t) {
|
|
1717
1706
|
if (e === t) return [];
|
|
1718
1707
|
const n = [], r = Mn(e, t);
|
|
1719
|
-
if (
|
|
1708
|
+
if (Pn.has(r)) {
|
|
1720
1709
|
for (const i of $t)
|
|
1721
|
-
n.push(
|
|
1710
|
+
n.push(Dn(r, i));
|
|
1722
1711
|
return n;
|
|
1723
1712
|
}
|
|
1724
1713
|
const s = Mn(t, e);
|
|
1725
|
-
if (
|
|
1714
|
+
if (Pn.has(s)) {
|
|
1726
1715
|
for (let i = $s - 1; i >= 0; i--)
|
|
1727
|
-
n.push(
|
|
1716
|
+
n.push(Dn(s, $t[i]));
|
|
1728
1717
|
return n;
|
|
1729
1718
|
}
|
|
1730
1719
|
return [];
|
|
@@ -1747,11 +1736,11 @@ function zs(e, t, n) {
|
|
|
1747
1736
|
}
|
|
1748
1737
|
const Ys = [0.32, 0.24, 0.16, 0.08, 0], Js = Ys.map(
|
|
1749
1738
|
(e) => `eyes_${e.toFixed(2)}`
|
|
1750
|
-
),
|
|
1739
|
+
), Qs = [
|
|
1751
1740
|
"eyes_0.32",
|
|
1752
1741
|
"eyes_0.16",
|
|
1753
1742
|
"eyes_0.00"
|
|
1754
|
-
],
|
|
1743
|
+
], Xs = [
|
|
1755
1744
|
"eyes_0.32",
|
|
1756
1745
|
"eyes_0.16",
|
|
1757
1746
|
"eyes_0.08",
|
|
@@ -1771,7 +1760,7 @@ function sn(e) {
|
|
|
1771
1760
|
function an(e) {
|
|
1772
1761
|
return ei[e];
|
|
1773
1762
|
}
|
|
1774
|
-
function
|
|
1763
|
+
function Ue(e) {
|
|
1775
1764
|
return Math.max(Zs, Math.min(qt, e));
|
|
1776
1765
|
}
|
|
1777
1766
|
function ti(e, t) {
|
|
@@ -1805,27 +1794,27 @@ const ni = {
|
|
|
1805
1794
|
disgust: "disgust",
|
|
1806
1795
|
disgusted: "disgust"
|
|
1807
1796
|
};
|
|
1808
|
-
function
|
|
1797
|
+
function ze(e, t = "neutral") {
|
|
1809
1798
|
const n = String(e ?? "").trim().toLowerCase();
|
|
1810
1799
|
return n ? ni[n] ?? t : t;
|
|
1811
1800
|
}
|
|
1812
|
-
function
|
|
1801
|
+
function or(e) {
|
|
1813
1802
|
return e === 0 ? null : tn(sn(e), "eyes_standard");
|
|
1814
1803
|
}
|
|
1815
|
-
function
|
|
1816
|
-
return
|
|
1804
|
+
function cr(e) {
|
|
1805
|
+
return or(an(e));
|
|
1817
1806
|
}
|
|
1818
|
-
function
|
|
1807
|
+
function Bn(e, t) {
|
|
1819
1808
|
const n = sn(an(e));
|
|
1820
|
-
return !t || t === "eyes_standard" ?
|
|
1809
|
+
return !t || t === "eyes_standard" ? cr(e) : e === "neutral" && t === "eyes_standard" ? null : tn(n, t);
|
|
1821
1810
|
}
|
|
1822
1811
|
function ri(e, t) {
|
|
1823
1812
|
const n = [];
|
|
1824
1813
|
for (const r of t)
|
|
1825
|
-
n.push(
|
|
1814
|
+
n.push(Bn(e, r));
|
|
1826
1815
|
for (let r = t.length - 2; r >= 0; r--)
|
|
1827
|
-
n.push(
|
|
1828
|
-
return n.push(
|
|
1816
|
+
n.push(Bn(e, t[r]));
|
|
1817
|
+
return n.push(cr(e)), n;
|
|
1829
1818
|
}
|
|
1830
1819
|
function si(e) {
|
|
1831
1820
|
return e === 0 ? null : tn(sn(e), "eyes_standard");
|
|
@@ -1841,25 +1830,25 @@ function oi(e, t) {
|
|
|
1841
1830
|
return null;
|
|
1842
1831
|
}
|
|
1843
1832
|
function ci(e) {
|
|
1844
|
-
const t =
|
|
1845
|
-
return t >= qt ? qt :
|
|
1833
|
+
const t = Ue(e);
|
|
1834
|
+
return t >= qt ? qt : Ue(t + ai);
|
|
1846
1835
|
}
|
|
1847
1836
|
function ui(e, t, n) {
|
|
1848
|
-
const r =
|
|
1837
|
+
const r = Ue(n);
|
|
1849
1838
|
return oi(t, e)?.emphasis ? ci(r) : r;
|
|
1850
1839
|
}
|
|
1851
|
-
function
|
|
1840
|
+
function Cn(e) {
|
|
1852
1841
|
if (!e) return 0;
|
|
1853
1842
|
const t = e.match(/^brow_(-?\d+)\//);
|
|
1854
1843
|
if (!t?.[1]) return null;
|
|
1855
1844
|
const n = Number.parseInt(t[1], 10);
|
|
1856
|
-
return Number.isFinite(n) ?
|
|
1845
|
+
return Number.isFinite(n) ? Ue(n) : null;
|
|
1857
1846
|
}
|
|
1858
|
-
function
|
|
1847
|
+
function lt(e, t) {
|
|
1859
1848
|
return e + Math.random() * (t - e);
|
|
1860
1849
|
}
|
|
1861
|
-
function
|
|
1862
|
-
return
|
|
1850
|
+
function vt() {
|
|
1851
|
+
return lt(14, 32);
|
|
1863
1852
|
}
|
|
1864
1853
|
function li(e = {}) {
|
|
1865
1854
|
const {
|
|
@@ -1871,126 +1860,126 @@ function li(e = {}) {
|
|
|
1871
1860
|
doubleBlinkGapMaxMs: a = 220,
|
|
1872
1861
|
fullBlinkChance: o = 0.75,
|
|
1873
1862
|
postEmotionChangeDelayMs: d = 380,
|
|
1874
|
-
minDwellMs:
|
|
1863
|
+
minDwellMs: f = 550
|
|
1875
1864
|
} = e;
|
|
1876
|
-
let c = "neutral", u = "neutral",
|
|
1865
|
+
let c = "neutral", u = "neutral", m = 0, g = 0, E = 0, h = {
|
|
1877
1866
|
kind: "idle",
|
|
1878
1867
|
nextBlinkAt: performance.now() + t
|
|
1879
|
-
},
|
|
1880
|
-
function
|
|
1881
|
-
|
|
1868
|
+
}, D = null, _ = "__eyes_open__|neutral|brow:0";
|
|
1869
|
+
function P(S = c) {
|
|
1870
|
+
_ = `${D ?? "__eyes_open__"}|${S}|brow:${g}`;
|
|
1882
1871
|
}
|
|
1883
|
-
function
|
|
1884
|
-
|
|
1885
|
-
const
|
|
1886
|
-
|
|
1872
|
+
function p(S, b = c) {
|
|
1873
|
+
D = S;
|
|
1874
|
+
const A = Cn(S);
|
|
1875
|
+
A != null ? g = A : S == null && (g = 0), P(b);
|
|
1887
1876
|
}
|
|
1888
|
-
function
|
|
1889
|
-
return
|
|
1877
|
+
function k(S) {
|
|
1878
|
+
return or(S);
|
|
1890
1879
|
}
|
|
1891
|
-
function
|
|
1892
|
-
const
|
|
1893
|
-
if (
|
|
1894
|
-
|
|
1880
|
+
function x(S, b, A) {
|
|
1881
|
+
const ne = Ue(b), M = Ue(A);
|
|
1882
|
+
if (m = M, ne === M) {
|
|
1883
|
+
p(k(M));
|
|
1895
1884
|
return;
|
|
1896
1885
|
}
|
|
1897
|
-
const
|
|
1898
|
-
...ii(
|
|
1899
|
-
|
|
1886
|
+
const Y = [
|
|
1887
|
+
...ii(ne, M),
|
|
1888
|
+
k(M)
|
|
1900
1889
|
];
|
|
1901
|
-
|
|
1890
|
+
h = {
|
|
1902
1891
|
kind: "browBlend",
|
|
1903
|
-
paths:
|
|
1892
|
+
paths: Y,
|
|
1904
1893
|
index: 0,
|
|
1905
|
-
holdUntil:
|
|
1906
|
-
targetBrow:
|
|
1907
|
-
},
|
|
1894
|
+
holdUntil: S + vt(),
|
|
1895
|
+
targetBrow: M
|
|
1896
|
+
}, p(Y[0] ?? null);
|
|
1908
1897
|
}
|
|
1909
|
-
function
|
|
1910
|
-
|
|
1898
|
+
function R(S, b) {
|
|
1899
|
+
h = {
|
|
1911
1900
|
kind: "idle",
|
|
1912
|
-
nextBlinkAt:
|
|
1913
|
-
}, u =
|
|
1901
|
+
nextBlinkAt: S + lt(n, r)
|
|
1902
|
+
}, u = b, p(k(m), b);
|
|
1914
1903
|
}
|
|
1915
|
-
function
|
|
1916
|
-
const
|
|
1917
|
-
|
|
1904
|
+
function K(S, b, A) {
|
|
1905
|
+
const ne = A ? Qs : Math.random() < o ? Js : Xs;
|
|
1906
|
+
h = {
|
|
1918
1907
|
kind: "playing",
|
|
1919
|
-
paths: ri(
|
|
1908
|
+
paths: ri(b, ne),
|
|
1920
1909
|
index: 0,
|
|
1921
|
-
holdUntil:
|
|
1910
|
+
holdUntil: S + vt(),
|
|
1922
1911
|
after: "idle",
|
|
1923
|
-
blinkEmotion:
|
|
1924
|
-
}, u =
|
|
1912
|
+
blinkEmotion: b
|
|
1913
|
+
}, u = b, p(h.paths[0] ?? null, b);
|
|
1925
1914
|
}
|
|
1926
|
-
function
|
|
1927
|
-
if (
|
|
1928
|
-
for (;
|
|
1929
|
-
|
|
1930
|
-
const
|
|
1931
|
-
|
|
1915
|
+
function B(S) {
|
|
1916
|
+
if (h.kind === "browBlend") {
|
|
1917
|
+
for (; S >= h.holdUntil && h.index < h.paths.length - 1; )
|
|
1918
|
+
h.index += 1, h.holdUntil = S + vt();
|
|
1919
|
+
const b = h.paths[h.index] ?? null;
|
|
1920
|
+
p(b), S >= h.holdUntil && h.index >= h.paths.length - 1 && (g = h.targetBrow, m = h.targetBrow, p(k(h.targetBrow)), h = {
|
|
1932
1921
|
kind: "idle",
|
|
1933
|
-
nextBlinkAt:
|
|
1922
|
+
nextBlinkAt: S + d
|
|
1934
1923
|
});
|
|
1935
1924
|
return;
|
|
1936
1925
|
}
|
|
1937
|
-
if (
|
|
1938
|
-
|
|
1926
|
+
if (h.kind === "idle") {
|
|
1927
|
+
p(k(m), u), S >= h.nextBlinkAt && K(S, u, !1);
|
|
1939
1928
|
return;
|
|
1940
1929
|
}
|
|
1941
|
-
if (
|
|
1942
|
-
|
|
1930
|
+
if (h.kind === "doublePause") {
|
|
1931
|
+
p(k(m), h.blinkEmotion), S >= h.resumeAt && K(S, h.blinkEmotion, !0);
|
|
1943
1932
|
return;
|
|
1944
1933
|
}
|
|
1945
|
-
if (
|
|
1946
|
-
for (;
|
|
1947
|
-
|
|
1948
|
-
if (h
|
|
1949
|
-
if (
|
|
1950
|
-
|
|
1934
|
+
if (h.kind === "playing") {
|
|
1935
|
+
for (; S >= h.holdUntil && h.index < h.paths.length - 1; )
|
|
1936
|
+
h.index += 1, h.holdUntil = S + vt();
|
|
1937
|
+
if (p(h.paths[h.index] ?? null, h.blinkEmotion), S >= h.holdUntil && h.index >= h.paths.length - 1) {
|
|
1938
|
+
if (h.after === "resumeIdle") {
|
|
1939
|
+
R(S + d, c);
|
|
1951
1940
|
return;
|
|
1952
1941
|
}
|
|
1953
|
-
if (
|
|
1954
|
-
|
|
1942
|
+
if (h.after === "doublePause") {
|
|
1943
|
+
h = {
|
|
1955
1944
|
kind: "doublePause",
|
|
1956
|
-
resumeAt:
|
|
1957
|
-
blinkEmotion:
|
|
1958
|
-
},
|
|
1945
|
+
resumeAt: S + lt(i, a),
|
|
1946
|
+
blinkEmotion: h.blinkEmotion
|
|
1947
|
+
}, p(k(m), h.blinkEmotion);
|
|
1959
1948
|
return;
|
|
1960
1949
|
}
|
|
1961
|
-
if (
|
|
1962
|
-
|
|
1950
|
+
if (h.after === "idle" && Math.random() < s) {
|
|
1951
|
+
h = {
|
|
1963
1952
|
kind: "doublePause",
|
|
1964
|
-
resumeAt:
|
|
1965
|
-
blinkEmotion:
|
|
1966
|
-
},
|
|
1953
|
+
resumeAt: S + lt(i, a),
|
|
1954
|
+
blinkEmotion: h.blinkEmotion
|
|
1955
|
+
}, p(k(m), h.blinkEmotion);
|
|
1967
1956
|
return;
|
|
1968
1957
|
}
|
|
1969
|
-
|
|
1958
|
+
R(S, h.blinkEmotion);
|
|
1970
1959
|
}
|
|
1971
1960
|
}
|
|
1972
1961
|
}
|
|
1973
1962
|
return {
|
|
1974
|
-
advance:
|
|
1975
|
-
setTargetEmotion(
|
|
1976
|
-
const
|
|
1977
|
-
if (
|
|
1978
|
-
const
|
|
1979
|
-
|
|
1980
|
-
},
|
|
1981
|
-
setTargetEyebrow(
|
|
1982
|
-
const
|
|
1983
|
-
if (
|
|
1984
|
-
const
|
|
1985
|
-
|
|
1963
|
+
advance: B,
|
|
1964
|
+
setTargetEmotion(S) {
|
|
1965
|
+
const b = ze(S, c);
|
|
1966
|
+
if (b === c) return;
|
|
1967
|
+
const A = performance.now();
|
|
1968
|
+
f > 0 && b !== c && !(c === "neutral" && b !== "neutral") && A - E < f || (c = b, u = b, E = A);
|
|
1969
|
+
},
|
|
1970
|
+
setTargetEyebrow(S) {
|
|
1971
|
+
const b = Ue(S);
|
|
1972
|
+
if (b === m) return;
|
|
1973
|
+
const A = performance.now(), ne = h.kind === "browBlend" ? Cn(D) ?? g : g;
|
|
1974
|
+
m = b, !(b === ne && h.kind !== "browBlend") && (h.kind === "playing" || h.kind === "doublePause" || x(A, ne, b));
|
|
1986
1975
|
},
|
|
1987
1976
|
getTargetEmotion: () => c,
|
|
1988
|
-
getTargetEyebrow: () =>
|
|
1989
|
-
getExpressionPath: () =>
|
|
1990
|
-
getDrawKey: () =>
|
|
1977
|
+
getTargetEyebrow: () => m,
|
|
1978
|
+
getExpressionPath: () => D,
|
|
1979
|
+
getDrawKey: () => _,
|
|
1991
1980
|
reset() {
|
|
1992
|
-
c = "neutral", u = "neutral",
|
|
1993
|
-
performance.now() +
|
|
1981
|
+
c = "neutral", u = "neutral", m = 0, g = 0, E = 0, R(
|
|
1982
|
+
performance.now() + lt(n, r),
|
|
1994
1983
|
"neutral"
|
|
1995
1984
|
);
|
|
1996
1985
|
}
|
|
@@ -2007,8 +1996,8 @@ function fi() {
|
|
|
2007
1996
|
async load(i) {
|
|
2008
1997
|
t && r === i || (s(), t = !1, r = i, i.startsWith("blob:") && (n = i), await new Promise((a, o) => {
|
|
2009
1998
|
const d = () => {
|
|
2010
|
-
const
|
|
2011
|
-
if (!Number.isFinite(
|
|
1999
|
+
const f = e.duration;
|
|
2000
|
+
if (!Number.isFinite(f) || f <= 0) {
|
|
2012
2001
|
o(new Error(`Idle video has invalid duration: ${i}`));
|
|
2013
2002
|
return;
|
|
2014
2003
|
}
|
|
@@ -2039,7 +2028,7 @@ function fi() {
|
|
|
2039
2028
|
}
|
|
2040
2029
|
};
|
|
2041
2030
|
}
|
|
2042
|
-
const di = 50,
|
|
2031
|
+
const di = 50, ur = 400;
|
|
2043
2032
|
function mi(e, t, n) {
|
|
2044
2033
|
return e.filter((r) => {
|
|
2045
2034
|
const s = r.queueIndex ?? -1;
|
|
@@ -2059,29 +2048,29 @@ function hi(e, t) {
|
|
|
2059
2048
|
n.push({
|
|
2060
2049
|
sentence: r,
|
|
2061
2050
|
startMs: Math.max(0, i.wtime - di),
|
|
2062
|
-
endMs: a.wtime + a.wduration +
|
|
2051
|
+
endMs: a.wtime + a.wduration + ur
|
|
2063
2052
|
});
|
|
2064
2053
|
}
|
|
2065
2054
|
return n.sort((r, s) => r.startMs - s.startMs);
|
|
2066
2055
|
}
|
|
2067
2056
|
function pi(e, t, n, r = "neutral") {
|
|
2068
|
-
const s =
|
|
2057
|
+
const s = ze(r);
|
|
2069
2058
|
if (t.length === 0) return s;
|
|
2070
2059
|
if (n.length === 0 || e < n[0].wtime)
|
|
2071
|
-
return
|
|
2060
|
+
return ze(t[0]?.emotion, s);
|
|
2072
2061
|
const i = hi(t, n);
|
|
2073
2062
|
let a = null;
|
|
2074
|
-
for (const
|
|
2075
|
-
e >=
|
|
2063
|
+
for (const f of i)
|
|
2064
|
+
e >= f.startMs && e <= f.endMs && (a = f);
|
|
2076
2065
|
if (a)
|
|
2077
|
-
return
|
|
2066
|
+
return ze(a.sentence.emotion, s);
|
|
2078
2067
|
const o = n[n.length - 1], d = o.wtime + o.wduration;
|
|
2079
|
-
return e > d +
|
|
2068
|
+
return e > d + ur ? ze(
|
|
2080
2069
|
t[t.length - 1]?.emotion,
|
|
2081
2070
|
s
|
|
2082
2071
|
) : s;
|
|
2083
2072
|
}
|
|
2084
|
-
function on(e, t, n, r, s =
|
|
2073
|
+
function on(e, t, n, r, s = sr) {
|
|
2085
2074
|
const i = new OffscreenCanvas(n, r), a = i.getContext("2d", { willReadFrequently: !0 });
|
|
2086
2075
|
a.drawImage(e, 0, 0, n, r);
|
|
2087
2076
|
const o = a.getImageData(0, 0, n, r), d = a.createImageData(n, r);
|
|
@@ -2089,22 +2078,22 @@ function on(e, t, n, r, s = rr) {
|
|
|
2089
2078
|
const c = new OffscreenCanvas(n, r).getContext("2d", { willReadFrequently: !0 });
|
|
2090
2079
|
for (const u of t) {
|
|
2091
2080
|
c.clearRect(0, 0, n, r), c.drawImage(u, 0, 0, n, r);
|
|
2092
|
-
const
|
|
2093
|
-
for (let
|
|
2094
|
-
const
|
|
2095
|
-
Math.max(
|
|
2081
|
+
const m = c.getImageData(0, 0, n, r);
|
|
2082
|
+
for (let g = 0; g < d.data.length; g += 4) {
|
|
2083
|
+
const E = m.data[g], h = m.data[g + 1], D = m.data[g + 2];
|
|
2084
|
+
Math.max(E, h, D) > s && (d.data[g] = E, d.data[g + 1] = h, d.data[g + 2] = D, d.data[g + 3] = 255);
|
|
2096
2085
|
}
|
|
2097
2086
|
}
|
|
2098
2087
|
return a.putImageData(d, 0, 0), i;
|
|
2099
2088
|
}
|
|
2100
|
-
let
|
|
2089
|
+
let Oe = null, Qe = null;
|
|
2101
2090
|
const Tt = /* @__PURE__ */ new Map();
|
|
2102
2091
|
function wi() {
|
|
2103
|
-
|
|
2092
|
+
Oe = null, Qe = null, Tt.clear();
|
|
2104
2093
|
}
|
|
2105
2094
|
Xr(wi);
|
|
2106
2095
|
function gi(e) {
|
|
2107
|
-
return e ??
|
|
2096
|
+
return e ?? Qe ?? void 0;
|
|
2108
2097
|
}
|
|
2109
2098
|
function cn(e) {
|
|
2110
2099
|
return new Promise((t, n) => {
|
|
@@ -2113,53 +2102,53 @@ function cn(e) {
|
|
|
2113
2102
|
});
|
|
2114
2103
|
}
|
|
2115
2104
|
async function yi(e) {
|
|
2116
|
-
return
|
|
2117
|
-
await
|
|
2105
|
+
return Pt() ? Vs(
|
|
2106
|
+
await Rt(bn(), e ?? "")
|
|
2118
2107
|
) : cn(bn());
|
|
2119
2108
|
}
|
|
2120
|
-
async function
|
|
2121
|
-
const s = n ? await
|
|
2122
|
-
if (!
|
|
2123
|
-
return
|
|
2109
|
+
async function xn(e, t, n, r) {
|
|
2110
|
+
const s = n ? await Os(e, r) : await fetch(e).then((f) => {
|
|
2111
|
+
if (!f.ok) throw new Error(`Failed to load ${e}`);
|
|
2112
|
+
return f.json();
|
|
2124
2113
|
}), i = s.sheets?.[0];
|
|
2125
2114
|
if (!i?.path) throw new Error(`${e} has no sheets[0].path`);
|
|
2126
2115
|
const a = n ? await Us(
|
|
2127
|
-
await
|
|
2116
|
+
await Rt(
|
|
2128
2117
|
zs(t, i.path, n),
|
|
2129
2118
|
r ?? ""
|
|
2130
2119
|
)
|
|
2131
2120
|
) : await cn(`${t}/${i.path}`), o = /* @__PURE__ */ new Map();
|
|
2132
|
-
for (const
|
|
2133
|
-
|
|
2121
|
+
for (const f of s.cells ?? [])
|
|
2122
|
+
f.path && o.set(f.path, f);
|
|
2134
2123
|
const d = /* @__PURE__ */ new Map();
|
|
2135
|
-
for (const
|
|
2136
|
-
d.set(
|
|
2124
|
+
for (const f of s.sheets ?? [])
|
|
2125
|
+
d.set(f.index, f);
|
|
2137
2126
|
return { atlas: a, atlasMeta: s, cellByPath: o, sheetByIndex: d, diffBase: t };
|
|
2138
2127
|
}
|
|
2139
2128
|
async function Kt(e) {
|
|
2140
|
-
const t = gi(e), n =
|
|
2129
|
+
const t = gi(e), n = Pt();
|
|
2141
2130
|
if (n && !t)
|
|
2142
2131
|
throw new Error("Encrypted assets enabled but no key provided");
|
|
2143
|
-
if (
|
|
2144
|
-
const i = await
|
|
2132
|
+
if (Oe && (!n || Qe === (t ?? null))) {
|
|
2133
|
+
const i = await Oe;
|
|
2145
2134
|
return {
|
|
2146
2135
|
...Xe(i),
|
|
2147
2136
|
visemePaths: [...i.viseme.cellByPath.keys()]
|
|
2148
2137
|
};
|
|
2149
2138
|
}
|
|
2150
|
-
|
|
2151
|
-
const r =
|
|
2152
|
-
|
|
2153
|
-
const i = await yi(t), a = await
|
|
2154
|
-
|
|
2139
|
+
Qe = t ?? null, Tt.clear();
|
|
2140
|
+
const r = es();
|
|
2141
|
+
Oe = (async () => {
|
|
2142
|
+
const i = await yi(t), a = await xn(
|
|
2143
|
+
ts(),
|
|
2155
2144
|
r,
|
|
2156
2145
|
n,
|
|
2157
2146
|
t
|
|
2158
2147
|
);
|
|
2159
2148
|
let o = null;
|
|
2160
2149
|
try {
|
|
2161
|
-
o = await
|
|
2162
|
-
|
|
2150
|
+
o = await xn(
|
|
2151
|
+
ns(),
|
|
2163
2152
|
r,
|
|
2164
2153
|
n,
|
|
2165
2154
|
t
|
|
@@ -2169,12 +2158,12 @@ async function Kt(e) {
|
|
|
2169
2158
|
}
|
|
2170
2159
|
return { sil: i, viseme: a, expression: o };
|
|
2171
2160
|
})();
|
|
2172
|
-
const s = await
|
|
2161
|
+
const s = await Oe;
|
|
2173
2162
|
return { ...Xe(s), visemePaths: [...s.viseme.cellByPath.keys()] };
|
|
2174
2163
|
}
|
|
2175
2164
|
async function un(e) {
|
|
2176
|
-
if (await Kt(e), !
|
|
2177
|
-
return
|
|
2165
|
+
if (await Kt(e), !Oe) throw new Error("Assets not loaded");
|
|
2166
|
+
return Oe;
|
|
2178
2167
|
}
|
|
2179
2168
|
function Xe(e) {
|
|
2180
2169
|
return Fs(
|
|
@@ -2193,55 +2182,55 @@ async function At(e, t, n) {
|
|
|
2193
2182
|
const i = (async () => {
|
|
2194
2183
|
const a = t.cellByPath.get(n);
|
|
2195
2184
|
if (!a) throw new Error(`No atlas cell for path: ${n}`);
|
|
2196
|
-
const o =
|
|
2197
|
-
if (
|
|
2198
|
-
const u = _i(t, a),
|
|
2199
|
-
|
|
2200
|
-
const
|
|
2201
|
-
return
|
|
2185
|
+
const o = Ls(t.atlasMeta, a), d = Xe(e);
|
|
2186
|
+
if (Ns(a)) {
|
|
2187
|
+
const u = _i(t, a), m = document.createElement("canvas");
|
|
2188
|
+
m.width = d.width, m.height = d.height;
|
|
2189
|
+
const g = m.getContext("2d");
|
|
2190
|
+
return g.fillStyle = "#000", g.fillRect(0, 0, d.width, d.height), g.drawImage(u, o.x, o.y), m;
|
|
2202
2191
|
}
|
|
2203
|
-
const
|
|
2192
|
+
const f = `${t.diffBase}/${n}`, c = await cn(f);
|
|
2204
2193
|
if (c.naturalWidth === d.width && c.naturalHeight === d.height)
|
|
2205
2194
|
return c;
|
|
2206
2195
|
throw new Error(`Diff PNG wrong size for ${n}`);
|
|
2207
2196
|
})();
|
|
2208
2197
|
return Tt.set(r, i), i;
|
|
2209
2198
|
}
|
|
2210
|
-
async function
|
|
2199
|
+
async function Fn(e, t, n, r, s, i) {
|
|
2211
2200
|
if (s) {
|
|
2212
|
-
const { width:
|
|
2201
|
+
const { width: g, height: E } = s;
|
|
2213
2202
|
if (i && !i() || t.readyState < HTMLMediaElement.HAVE_CURRENT_DATA)
|
|
2214
2203
|
return;
|
|
2215
|
-
const
|
|
2216
|
-
|
|
2217
|
-
const
|
|
2218
|
-
if (
|
|
2219
|
-
(e.width !==
|
|
2220
|
-
const
|
|
2221
|
-
|
|
2204
|
+
const h = document.createElement("canvas");
|
|
2205
|
+
h.width = g, h.height = E;
|
|
2206
|
+
const D = h.getContext("2d");
|
|
2207
|
+
if (D.clearRect(0, 0, g, E), D.drawImage(t, 0, 0, g, E), i && !i()) return;
|
|
2208
|
+
(e.width !== g || e.height !== E) && (e.width = g, e.height = E);
|
|
2209
|
+
const _ = e.getContext("2d");
|
|
2210
|
+
_.clearRect(0, 0, g, E), _.drawImage(h, 0, 0);
|
|
2222
2211
|
return;
|
|
2223
2212
|
}
|
|
2224
|
-
const a = await un(), o = nn(a.viseme.atlasMeta), { width: d, height:
|
|
2225
|
-
(e.width !== d || e.height !==
|
|
2213
|
+
const a = await un(), o = nn(a.viseme.atlasMeta), { width: d, height: f } = Xe(a);
|
|
2214
|
+
(e.width !== d || e.height !== f) && (e.width = d, e.height = f);
|
|
2226
2215
|
const c = [], u = e.getContext("2d");
|
|
2227
|
-
if (u.clearRect(0, 0, d,
|
|
2228
|
-
const
|
|
2229
|
-
u.drawImage(
|
|
2216
|
+
if (u.clearRect(0, 0, d, f), t.readyState < HTMLMediaElement.HAVE_CURRENT_DATA) {
|
|
2217
|
+
const g = a.sil;
|
|
2218
|
+
u.drawImage(g, 0, 0, d, f);
|
|
2230
2219
|
return;
|
|
2231
2220
|
}
|
|
2232
2221
|
if (c.length === 0) {
|
|
2233
|
-
u.drawImage(t, 0, 0, d,
|
|
2222
|
+
u.drawImage(t, 0, 0, d, f);
|
|
2234
2223
|
return;
|
|
2235
2224
|
}
|
|
2236
|
-
const
|
|
2237
|
-
u.drawImage(
|
|
2225
|
+
const m = on(t, c, d, f, o);
|
|
2226
|
+
u.drawImage(m, 0, 0);
|
|
2238
2227
|
}
|
|
2239
2228
|
async function Gt(e, t, n) {
|
|
2240
|
-
const r = await un(
|
|
2229
|
+
const r = await un(Qe ?? void 0), s = nn(r.viseme.atlasMeta), { width: i, height: a } = Xe(r);
|
|
2241
2230
|
(e.width !== i || e.height !== a) && (e.width = i, e.height = a);
|
|
2242
2231
|
const o = [];
|
|
2243
2232
|
if (t.mouthPath) {
|
|
2244
|
-
const c = new Set(r.viseme.cellByPath.keys()), u =
|
|
2233
|
+
const c = new Set(r.viseme.cellByPath.keys()), u = ir(t.mouthPath, c) ?? (c.has(t.mouthPath) ? t.mouthPath : null);
|
|
2245
2234
|
u && o.push(await At(r, r.viseme, u));
|
|
2246
2235
|
}
|
|
2247
2236
|
t.expressionPath && r.expression && o.push(
|
|
@@ -2252,19 +2241,19 @@ async function Gt(e, t, n) {
|
|
|
2252
2241
|
d.drawImage(r.sil, 0, 0, i, a);
|
|
2253
2242
|
return;
|
|
2254
2243
|
}
|
|
2255
|
-
const
|
|
2244
|
+
const f = on(
|
|
2256
2245
|
r.sil,
|
|
2257
2246
|
o,
|
|
2258
2247
|
i,
|
|
2259
2248
|
a,
|
|
2260
2249
|
s
|
|
2261
2250
|
);
|
|
2262
|
-
d.drawImage(
|
|
2251
|
+
d.drawImage(f, 0, 0);
|
|
2263
2252
|
}
|
|
2264
2253
|
async function Si(e, t) {
|
|
2265
|
-
const n = await un(
|
|
2254
|
+
const n = await un(Qe ?? void 0), r = nn(n.viseme.atlasMeta), { width: s, height: i } = Xe(n), a = [];
|
|
2266
2255
|
if (e.mouthPath) {
|
|
2267
|
-
const c = new Set(n.viseme.cellByPath.keys()), u =
|
|
2256
|
+
const c = new Set(n.viseme.cellByPath.keys()), u = ir(e.mouthPath, c) ?? (c.has(e.mouthPath) ? e.mouthPath : null);
|
|
2268
2257
|
u && a.push(await At(n, n.viseme, u));
|
|
2269
2258
|
}
|
|
2270
2259
|
e.expressionPath && n.expression && a.push(
|
|
@@ -2273,29 +2262,29 @@ async function Si(e, t) {
|
|
|
2273
2262
|
const o = new OffscreenCanvas(s, i), d = o.getContext("2d");
|
|
2274
2263
|
if (a.length === 0)
|
|
2275
2264
|
return d.drawImage(n.sil, 0, 0, s, i), o.transferToImageBitmap();
|
|
2276
|
-
const
|
|
2265
|
+
const f = on(
|
|
2277
2266
|
n.sil,
|
|
2278
2267
|
a,
|
|
2279
2268
|
s,
|
|
2280
2269
|
i,
|
|
2281
2270
|
r
|
|
2282
2271
|
);
|
|
2283
|
-
return d.drawImage(
|
|
2272
|
+
return d.drawImage(f, 0, 0), o.transferToImageBitmap();
|
|
2284
2273
|
}
|
|
2285
|
-
async function
|
|
2274
|
+
async function vi(e) {
|
|
2286
2275
|
await Gt(e, { mouthPath: null, expressionPath: null });
|
|
2287
2276
|
}
|
|
2288
|
-
let
|
|
2289
|
-
function
|
|
2290
|
-
|
|
2277
|
+
let lr = null;
|
|
2278
|
+
function Ln(e) {
|
|
2279
|
+
lr = e;
|
|
2291
2280
|
}
|
|
2292
|
-
function
|
|
2293
|
-
return
|
|
2281
|
+
function Ve() {
|
|
2282
|
+
return lr;
|
|
2294
2283
|
}
|
|
2295
|
-
function
|
|
2284
|
+
function ki(e) {
|
|
2296
2285
|
return `${e.from}→${e.to}@${e.fromVtime}`;
|
|
2297
2286
|
}
|
|
2298
|
-
function
|
|
2287
|
+
function Nn() {
|
|
2299
2288
|
return {
|
|
2300
2289
|
rafTicksSpeaking: 0,
|
|
2301
2290
|
rafTicksDeduped: 0,
|
|
@@ -2314,14 +2303,14 @@ function On() {
|
|
|
2314
2303
|
};
|
|
2315
2304
|
}
|
|
2316
2305
|
function bi() {
|
|
2317
|
-
let e =
|
|
2306
|
+
let e = Nn();
|
|
2318
2307
|
const t = /* @__PURE__ */ new Set(), n = /* @__PURE__ */ new Set(), r = /* @__PURE__ */ new Set();
|
|
2319
2308
|
let s = "", i = -1, a = "";
|
|
2320
2309
|
const o = () => {
|
|
2321
|
-
e =
|
|
2310
|
+
e = Nn(), t.clear(), n.clear(), r.clear(), s = "", i = -1, a = "";
|
|
2322
2311
|
}, d = (c) => {
|
|
2323
2312
|
t.add(c);
|
|
2324
|
-
},
|
|
2313
|
+
}, f = (c) => {
|
|
2325
2314
|
c && r.add(c);
|
|
2326
2315
|
};
|
|
2327
2316
|
return {
|
|
@@ -2342,8 +2331,8 @@ function bi() {
|
|
|
2342
2331
|
e.workerStale += 1;
|
|
2343
2332
|
},
|
|
2344
2333
|
onTransitionSample(c, u) {
|
|
2345
|
-
const
|
|
2346
|
-
e.transitionFramesSampled += 1,
|
|
2334
|
+
const m = ki(c);
|
|
2335
|
+
e.transitionFramesSampled += 1, m !== s && (s = m, i = -1, a !== m && (a = m, e.rifeFramesOmittedByGap += c.omittedByGap)), u && n.add(u), i >= 0 && c.frameIdx > i + 1 && (e.transitionFramesMissed += c.frameIdx - i - 1), i = c.frameIdx;
|
|
2347
2336
|
},
|
|
2348
2337
|
onBufferTick() {
|
|
2349
2338
|
e.bufferTicks += 1;
|
|
@@ -2362,52 +2351,52 @@ function bi() {
|
|
|
2362
2351
|
onDrawDisplayed(c, u) {
|
|
2363
2352
|
if (e.drawsDisplayed += 1, c.transitionMeta) {
|
|
2364
2353
|
e.transitionFramesDisplayed += 1;
|
|
2365
|
-
const
|
|
2366
|
-
d(
|
|
2354
|
+
const g = c.transitionMeta;
|
|
2355
|
+
d(g.fromVtime), d(g.toVtime), f(c.mouthPath);
|
|
2367
2356
|
return;
|
|
2368
2357
|
}
|
|
2369
2358
|
if (c.label.includes("→")) {
|
|
2370
2359
|
e.transitionFramesDisplayed += 1;
|
|
2371
2360
|
return;
|
|
2372
2361
|
}
|
|
2373
|
-
const
|
|
2374
|
-
if (!(!
|
|
2375
|
-
for (const
|
|
2376
|
-
if (
|
|
2377
|
-
d(
|
|
2362
|
+
const m = c.label.trim();
|
|
2363
|
+
if (!(!m || m === "sil")) {
|
|
2364
|
+
for (const g of u)
|
|
2365
|
+
if (g.viseme === m && c.elapsedMs >= g.vtime && c.elapsedMs < g.vtime + g.vduration) {
|
|
2366
|
+
d(g.vtime);
|
|
2378
2367
|
break;
|
|
2379
2368
|
}
|
|
2380
2369
|
}
|
|
2381
2370
|
},
|
|
2382
2371
|
snapshot(c, u) {
|
|
2383
|
-
let
|
|
2384
|
-
for (const
|
|
2385
|
-
if (
|
|
2386
|
-
if (
|
|
2387
|
-
|
|
2372
|
+
let m = 0, g = 0;
|
|
2373
|
+
for (const P of c)
|
|
2374
|
+
if (P.viseme !== "sil") {
|
|
2375
|
+
if (P.vtime >= u) break;
|
|
2376
|
+
m += 1, t.has(P.vtime) && (g += 1);
|
|
2388
2377
|
}
|
|
2389
|
-
const
|
|
2378
|
+
const E = m > 0 ? Math.round(g / m * 100) : 100, h = e.queueSuperseded + e.workerStale + Math.max(0, e.drawsRequested - e.drawsDisplayed), D = m - g, _ = e.bufferTicks > 0 ? Math.round(e.bufferHits / e.bufferTicks * 100) : 100;
|
|
2390
2379
|
return {
|
|
2391
2380
|
...e,
|
|
2392
|
-
bufferHitRate:
|
|
2393
|
-
renderLoss:
|
|
2394
|
-
visemeSlotsTotal:
|
|
2395
|
-
visemeSlotsCovered:
|
|
2396
|
-
visemeCoveragePct:
|
|
2381
|
+
bufferHitRate: _,
|
|
2382
|
+
renderLoss: h,
|
|
2383
|
+
visemeSlotsTotal: m,
|
|
2384
|
+
visemeSlotsCovered: g,
|
|
2385
|
+
visemeCoveragePct: E,
|
|
2397
2386
|
transitionFramesUniqueSampled: n.size,
|
|
2398
2387
|
transitionFramesUniquePainted: r.size,
|
|
2399
2388
|
drawsDeduped: e.rafTicksDeduped,
|
|
2400
|
-
renderSkips: e.rafTicksDeduped +
|
|
2401
|
-
visemesShown:
|
|
2402
|
-
visemesSkipped:
|
|
2389
|
+
renderSkips: e.rafTicksDeduped + h,
|
|
2390
|
+
visemesShown: g,
|
|
2391
|
+
visemesSkipped: D,
|
|
2403
2392
|
rifeTransitionFramesSkipped: e.transitionFramesMissed
|
|
2404
2393
|
};
|
|
2405
2394
|
}
|
|
2406
2395
|
};
|
|
2407
2396
|
}
|
|
2408
|
-
const
|
|
2397
|
+
const fr = Yt, Ei = 200, Ti = 100, Ai = 600, dr = "__sil__";
|
|
2409
2398
|
function Ii(e) {
|
|
2410
|
-
return e.lastDrawnKey ? e.lastDrawnKey.split("|")[0] ===
|
|
2399
|
+
return e.lastDrawnKey ? e.lastDrawnKey.split("|")[0] === dr : !1;
|
|
2411
2400
|
}
|
|
2412
2401
|
function ln() {
|
|
2413
2402
|
return { lastDrawnKey: "" };
|
|
@@ -2415,45 +2404,50 @@ function ln() {
|
|
|
2415
2404
|
function ve(e) {
|
|
2416
2405
|
e.lastDrawnKey = "", e.transitionCache = void 0;
|
|
2417
2406
|
}
|
|
2418
|
-
function
|
|
2407
|
+
function Pi(e, t) {
|
|
2419
2408
|
if (t?.transitionCache && t.transitionCache.queueLength === e.length)
|
|
2420
2409
|
return t.transitionCache.transitions;
|
|
2421
|
-
const n =
|
|
2410
|
+
const n = ys(e);
|
|
2422
2411
|
return t && (t.transitionCache = { queueLength: e.length, transitions: n }), n;
|
|
2423
2412
|
}
|
|
2424
|
-
function
|
|
2413
|
+
function Mi(e, t) {
|
|
2425
2414
|
let n = "sil";
|
|
2426
2415
|
for (const r of e)
|
|
2427
2416
|
r.viseme !== "sil" && (t != null && r.vtime > t || (n = r.viseme));
|
|
2428
2417
|
return n;
|
|
2429
2418
|
}
|
|
2430
|
-
function
|
|
2419
|
+
function Di(e, t, n, r = 120) {
|
|
2431
2420
|
if (n !== "sil")
|
|
2432
2421
|
return n;
|
|
2433
|
-
const s =
|
|
2434
|
-
return s !== "sil" ? s :
|
|
2422
|
+
const s = Zn(e, t, r);
|
|
2423
|
+
return s !== "sil" ? s : Mi(e, t);
|
|
2435
2424
|
}
|
|
2436
|
-
function
|
|
2425
|
+
function Ri(e, t) {
|
|
2437
2426
|
return e === "sil" ? !1 : t ? qs(e, "sil", t) : rn(e, "sil").length > 0;
|
|
2438
2427
|
}
|
|
2439
|
-
function
|
|
2440
|
-
return
|
|
2428
|
+
function Bi() {
|
|
2429
|
+
return fr + Ai;
|
|
2441
2430
|
}
|
|
2442
2431
|
function It(e) {
|
|
2443
|
-
return e ??
|
|
2432
|
+
return e ?? dr;
|
|
2444
2433
|
}
|
|
2445
2434
|
function fn(e, t, n, r, s = Ti) {
|
|
2446
2435
|
if (e.length === 0)
|
|
2447
2436
|
return { diffPath: null, label: "sil" };
|
|
2448
2437
|
if (t >= Ne(e))
|
|
2449
2438
|
return { diffPath: null, label: "sil" };
|
|
2450
|
-
const i =
|
|
2439
|
+
const i = Pi(e, r), a = _s(i, t);
|
|
2451
2440
|
if (a) {
|
|
2452
|
-
const d =
|
|
2441
|
+
const d = Jn(
|
|
2442
|
+
a.fromVtime,
|
|
2443
|
+
a.toVtime,
|
|
2444
|
+
a.from,
|
|
2445
|
+
a.to
|
|
2446
|
+
);
|
|
2453
2447
|
if (t >= d.transStart && t < d.transEnd) {
|
|
2454
|
-
let
|
|
2455
|
-
n && (
|
|
2456
|
-
const c = Gs(
|
|
2448
|
+
let f = rn(a.from, a.to);
|
|
2449
|
+
n && (f = ar(f, n));
|
|
2450
|
+
const c = Gs(f, d.effectiveGapMs);
|
|
2457
2451
|
if (c.length > 0) {
|
|
2458
2452
|
const u = js(
|
|
2459
2453
|
t,
|
|
@@ -2471,55 +2465,55 @@ function fn(e, t, n, r, s = Ti) {
|
|
|
2471
2465
|
toVtime: a.toVtime,
|
|
2472
2466
|
frameIdx: u,
|
|
2473
2467
|
frameCount: c.length,
|
|
2474
|
-
fullFrameCount:
|
|
2475
|
-
omittedByGap: Math.max(0,
|
|
2468
|
+
fullFrameCount: f.length,
|
|
2469
|
+
omittedByGap: Math.max(0, f.length - c.length)
|
|
2476
2470
|
}
|
|
2477
2471
|
};
|
|
2478
2472
|
}
|
|
2479
2473
|
return { diffPath: Et(a.to), label: a.to };
|
|
2480
2474
|
}
|
|
2481
2475
|
}
|
|
2482
|
-
const o =
|
|
2476
|
+
const o = Zn(e, t, s);
|
|
2483
2477
|
return o === "sil" ? { diffPath: null, label: "sil" } : { diffPath: Et(o), label: o };
|
|
2484
2478
|
}
|
|
2485
2479
|
function dn(e, t) {
|
|
2486
2480
|
const n = t ?? It(e.expressionPath);
|
|
2487
2481
|
return `${It(e.mouthPath)}|${n}`;
|
|
2488
2482
|
}
|
|
2489
|
-
function Ci(e, t, n, r, s, i, a, o, d,
|
|
2483
|
+
function Ci(e, t, n, r, s, i, a, o, d, f) {
|
|
2490
2484
|
const c = fn(t, n, d, i), u = {
|
|
2491
2485
|
mouthPath: c.diffPath,
|
|
2492
2486
|
expressionPath: r
|
|
2493
|
-
},
|
|
2494
|
-
if (c.transitionMeta &&
|
|
2495
|
-
|
|
2487
|
+
}, m = dn(u, s), g = Ve();
|
|
2488
|
+
if (c.transitionMeta && g?.onTransitionSample(c.transitionMeta, c.diffPath), m === i.lastDrawnKey) {
|
|
2489
|
+
g?.onDrawDeduped();
|
|
2496
2490
|
return;
|
|
2497
2491
|
}
|
|
2498
|
-
|
|
2499
|
-
|
|
2492
|
+
g?.onDrawRequested(), o(c), i.lastDrawnKey = m, a(e, u, m, (E) => {
|
|
2493
|
+
E === m && (i.lastDrawnKey = m);
|
|
2500
2494
|
});
|
|
2501
2495
|
}
|
|
2502
|
-
function
|
|
2503
|
-
const o = { mouthPath: null, expressionPath: t }, d = a != null ? `|idle@${Math.round(a * 1e3)}` : "",
|
|
2504
|
-
!(a != null) &&
|
|
2496
|
+
function On(e, t, n, r, s, i, a = null) {
|
|
2497
|
+
const o = { mouthPath: null, expressionPath: t }, d = a != null ? `|idle@${Math.round(a * 1e3)}` : "", f = dn(o, n) + d;
|
|
2498
|
+
!(a != null) && f === r.lastDrawnKey || (i(
|
|
2505
2499
|
a != null ? "idle" : "sil"
|
|
2506
|
-
), s(e, o,
|
|
2507
|
-
u ===
|
|
2500
|
+
), s(e, o, f, (u) => {
|
|
2501
|
+
u === f && (r.lastDrawnKey = f);
|
|
2508
2502
|
}));
|
|
2509
2503
|
}
|
|
2510
|
-
function
|
|
2504
|
+
function mr(e, t, n, r, s = ft, i) {
|
|
2511
2505
|
if (n <= t || e.length === 0) return [];
|
|
2512
2506
|
const a = i ?? ln(), o = [];
|
|
2513
2507
|
let d = "";
|
|
2514
|
-
for (let
|
|
2508
|
+
for (let f = t; f < n; f += s) {
|
|
2515
2509
|
const c = fn(
|
|
2516
2510
|
e,
|
|
2517
|
-
|
|
2511
|
+
f,
|
|
2518
2512
|
r,
|
|
2519
2513
|
a
|
|
2520
2514
|
), u = It(c.diffPath);
|
|
2521
2515
|
u !== d && (d = u, o.push({
|
|
2522
|
-
displayAtMs:
|
|
2516
|
+
displayAtMs: f,
|
|
2523
2517
|
mouthPath: c.diffPath,
|
|
2524
2518
|
mouthKey: u,
|
|
2525
2519
|
label: c.label
|
|
@@ -2527,8 +2521,8 @@ function dr(e, t, n, r, s = lt, i) {
|
|
|
2527
2521
|
}
|
|
2528
2522
|
return o;
|
|
2529
2523
|
}
|
|
2530
|
-
const
|
|
2531
|
-
function
|
|
2524
|
+
const xi = 3;
|
|
2525
|
+
function hr(e) {
|
|
2532
2526
|
let t = 0;
|
|
2533
2527
|
const n = [];
|
|
2534
2528
|
let r = !1, s = !1;
|
|
@@ -2550,9 +2544,9 @@ function mr(e) {
|
|
|
2550
2544
|
}));
|
|
2551
2545
|
};
|
|
2552
2546
|
return {
|
|
2553
|
-
enqueue(o, d,
|
|
2547
|
+
enqueue(o, d, f) {
|
|
2554
2548
|
const c = n.findIndex((u) => u.drawKey === d);
|
|
2555
|
-
c >= 0 ? n[c] = { diffs: o, drawKey: d, onDisplayed:
|
|
2549
|
+
c >= 0 ? n[c] = { diffs: o, drawKey: d, onDisplayed: f } : (n.length >= xi && (n.shift(), Ve()?.onQueueSuperseded()), n.push({ diffs: o, drawKey: d, onDisplayed: f })), a();
|
|
2556
2550
|
},
|
|
2557
2551
|
reset() {
|
|
2558
2552
|
t += 1, n.length = 0;
|
|
@@ -2568,17 +2562,17 @@ function mr(e) {
|
|
|
2568
2562
|
function Fi(e, t = 2) {
|
|
2569
2563
|
const n = [], r = /* @__PURE__ */ new Set();
|
|
2570
2564
|
let s = 0, i = !1, a = 0;
|
|
2571
|
-
const o = (
|
|
2565
|
+
const o = (f, c) => `${f}|${c}`, d = async () => {
|
|
2572
2566
|
if (!i) {
|
|
2573
2567
|
i = !0;
|
|
2574
2568
|
try {
|
|
2575
2569
|
for (; s < t && n.length > 0; ) {
|
|
2576
|
-
const
|
|
2570
|
+
const f = n.shift(), c = o(f.displayAtMs, f.drawKey);
|
|
2577
2571
|
if (r.has(c)) continue;
|
|
2578
2572
|
r.add(c), s += 1;
|
|
2579
2573
|
const u = a;
|
|
2580
2574
|
try {
|
|
2581
|
-
await e(
|
|
2575
|
+
await e(f);
|
|
2582
2576
|
} finally {
|
|
2583
2577
|
if (r.delete(c), s -= 1, u !== a) return;
|
|
2584
2578
|
}
|
|
@@ -2589,14 +2583,14 @@ function Fi(e, t = 2) {
|
|
|
2589
2583
|
}
|
|
2590
2584
|
};
|
|
2591
2585
|
return {
|
|
2592
|
-
enqueue(
|
|
2593
|
-
const c = o(
|
|
2594
|
-
r.has(c) || n.some((u) => o(u.displayAtMs, u.drawKey) === c) || (n.push(
|
|
2586
|
+
enqueue(f) {
|
|
2587
|
+
const c = o(f.displayAtMs, f.drawKey);
|
|
2588
|
+
r.has(c) || n.some((u) => o(u.displayAtMs, u.drawKey) === c) || (n.push(f), d());
|
|
2595
2589
|
},
|
|
2596
|
-
isQueuedOrInflight(
|
|
2597
|
-
const u = o(
|
|
2590
|
+
isQueuedOrInflight(f, c) {
|
|
2591
|
+
const u = o(f, c);
|
|
2598
2592
|
return r.has(u) ? !0 : n.some(
|
|
2599
|
-
(
|
|
2593
|
+
(m) => o(m.displayAtMs, m.drawKey) === u
|
|
2600
2594
|
);
|
|
2601
2595
|
},
|
|
2602
2596
|
reset() {
|
|
@@ -2607,7 +2601,7 @@ function Fi(e, t = 2) {
|
|
|
2607
2601
|
}
|
|
2608
2602
|
};
|
|
2609
2603
|
}
|
|
2610
|
-
function
|
|
2604
|
+
function Li() {
|
|
2611
2605
|
const e = /* @__PURE__ */ new Map(), t = (n) => {
|
|
2612
2606
|
n.bitmap.close();
|
|
2613
2607
|
};
|
|
@@ -2642,13 +2636,13 @@ function Oi() {
|
|
|
2642
2636
|
}
|
|
2643
2637
|
};
|
|
2644
2638
|
}
|
|
2645
|
-
function
|
|
2646
|
-
const a =
|
|
2639
|
+
function Ni(e, t, n, r, s, i) {
|
|
2640
|
+
const a = mr(
|
|
2647
2641
|
t,
|
|
2648
2642
|
n,
|
|
2649
2643
|
r,
|
|
2650
2644
|
s,
|
|
2651
|
-
|
|
2645
|
+
ft,
|
|
2652
2646
|
i
|
|
2653
2647
|
);
|
|
2654
2648
|
if (a.length === 0) return { ready: 0, total: 0 };
|
|
@@ -2657,61 +2651,61 @@ function Li(e, t, n, r, s, i) {
|
|
|
2657
2651
|
e.has(d.displayAtMs, d.mouthKey) && (o += 1);
|
|
2658
2652
|
return { ready: o, total: a.length };
|
|
2659
2653
|
}
|
|
2660
|
-
function
|
|
2661
|
-
const t =
|
|
2654
|
+
function Oi(e) {
|
|
2655
|
+
const t = Li(), n = ln(), r = /* @__PURE__ */ new Set();
|
|
2662
2656
|
let s = "", i = null;
|
|
2663
2657
|
const a = Fi(
|
|
2664
2658
|
async (u) => {
|
|
2665
2659
|
try {
|
|
2666
2660
|
if (!e.supportsBufferedPlayback) return;
|
|
2667
|
-
const
|
|
2661
|
+
const m = await e.compositePrefetchFrame(
|
|
2668
2662
|
u.diffs,
|
|
2669
2663
|
u.mouthKey
|
|
2670
2664
|
);
|
|
2671
|
-
if (!
|
|
2665
|
+
if (!m) return;
|
|
2672
2666
|
t.markRendered(
|
|
2673
2667
|
u.displayAtMs,
|
|
2674
2668
|
u.mouthKey,
|
|
2675
2669
|
u.label,
|
|
2676
2670
|
u.mouthPath,
|
|
2677
|
-
|
|
2678
|
-
),
|
|
2671
|
+
m
|
|
2672
|
+
), Ve()?.onBufferPrefetched();
|
|
2679
2673
|
} finally {
|
|
2680
2674
|
r.delete(u.mouthKey);
|
|
2681
2675
|
}
|
|
2682
2676
|
},
|
|
2683
|
-
|
|
2677
|
+
Fr
|
|
2684
2678
|
), o = (u) => {
|
|
2685
|
-
for (const
|
|
2686
|
-
t.has(
|
|
2687
|
-
...
|
|
2679
|
+
for (const m of u)
|
|
2680
|
+
t.has(m.displayAtMs, m.mouthKey) || r.has(m.mouthKey) || a.isQueuedOrInflight(0, m.mouthKey) || (r.add(m.mouthKey), a.enqueue({
|
|
2681
|
+
...m,
|
|
2688
2682
|
displayAtMs: 0,
|
|
2689
|
-
drawKey:
|
|
2683
|
+
drawKey: m.mouthKey,
|
|
2690
2684
|
diffs: {
|
|
2691
|
-
mouthPath:
|
|
2685
|
+
mouthPath: m.mouthPath,
|
|
2692
2686
|
expressionPath: null
|
|
2693
2687
|
}
|
|
2694
2688
|
}));
|
|
2695
|
-
}, d = (u,
|
|
2689
|
+
}, d = (u, m, g, E = Ft) => {
|
|
2696
2690
|
if (!e.supportsBufferedPlayback) return;
|
|
2697
|
-
const
|
|
2691
|
+
const h = Math.max(0, m - ft * 4), D = mr(
|
|
2698
2692
|
u,
|
|
2699
|
-
|
|
2700
|
-
|
|
2701
|
-
|
|
2702
|
-
|
|
2693
|
+
h,
|
|
2694
|
+
m + E,
|
|
2695
|
+
g,
|
|
2696
|
+
ft,
|
|
2703
2697
|
n
|
|
2704
2698
|
);
|
|
2705
|
-
o(
|
|
2706
|
-
},
|
|
2707
|
-
s = u, i =
|
|
2708
|
-
}, c = (u,
|
|
2699
|
+
o(D);
|
|
2700
|
+
}, f = (u, m) => {
|
|
2701
|
+
s = u, i = m;
|
|
2702
|
+
}, c = (u, m) => !(s !== u || i !== m);
|
|
2709
2703
|
return {
|
|
2710
2704
|
reset() {
|
|
2711
|
-
t.reset(), a.reset(), r.clear(), ve(n), s = "", i = null,
|
|
2705
|
+
t.reset(), a.reset(), r.clear(), ve(n), s = "", i = null, Ve()?.onBufferReset();
|
|
2712
2706
|
},
|
|
2713
|
-
markExternallyDisplayed(u,
|
|
2714
|
-
|
|
2707
|
+
markExternallyDisplayed(u, m) {
|
|
2708
|
+
f(u.split("|")[0] ?? u, m);
|
|
2715
2709
|
},
|
|
2716
2710
|
warmupTick(u) {
|
|
2717
2711
|
e.supportsBufferedPlayback && d(
|
|
@@ -2721,52 +2715,52 @@ function Ni(e) {
|
|
|
2721
2715
|
Math.max(Sn, Ft)
|
|
2722
2716
|
);
|
|
2723
2717
|
},
|
|
2724
|
-
isWarmupReady(u,
|
|
2718
|
+
isWarmupReady(u, m = Sn) {
|
|
2725
2719
|
if (!e.supportsBufferedPlayback) return !0;
|
|
2726
|
-
const { ready:
|
|
2720
|
+
const { ready: g, total: E } = Ni(
|
|
2727
2721
|
t,
|
|
2728
2722
|
u.queue,
|
|
2729
2723
|
0,
|
|
2730
|
-
|
|
2724
|
+
m,
|
|
2731
2725
|
u.availablePaths,
|
|
2732
2726
|
n
|
|
2733
2727
|
);
|
|
2734
|
-
return
|
|
2728
|
+
return E === 0 ? !1 : g / E >= xr;
|
|
2735
2729
|
},
|
|
2736
2730
|
getBufferedFrameCount: () => t.size(),
|
|
2737
2731
|
tick(u) {
|
|
2738
|
-
const
|
|
2739
|
-
|
|
2732
|
+
const m = Ve();
|
|
2733
|
+
m?.onBufferTick(), d(
|
|
2740
2734
|
u.queue,
|
|
2741
2735
|
u.elapsedMs,
|
|
2742
2736
|
u.availablePaths
|
|
2743
2737
|
), t.pruneBefore(u.elapsedMs - Ft);
|
|
2744
|
-
const
|
|
2738
|
+
const g = fn(
|
|
2745
2739
|
u.queue,
|
|
2746
2740
|
u.elapsedMs,
|
|
2747
2741
|
u.availablePaths,
|
|
2748
2742
|
n
|
|
2749
|
-
),
|
|
2750
|
-
{ mouthPath:
|
|
2743
|
+
), E = It(g.diffPath), h = dn(
|
|
2744
|
+
{ mouthPath: g.diffPath, expressionPath: u.expressionPath },
|
|
2751
2745
|
u.expressionDrawKey
|
|
2752
|
-
),
|
|
2753
|
-
if (c(
|
|
2754
|
-
return
|
|
2755
|
-
const
|
|
2756
|
-
|
|
2746
|
+
), D = () => (f(E, u.expressionPath), m?.onBufferHit(), { usedBuffer: !0, underrun: !1, held: !0 });
|
|
2747
|
+
if (c(E, u.expressionPath) || u.playbackState.lastDrawnKey === h)
|
|
2748
|
+
return D();
|
|
2749
|
+
const _ = t.findForMouthKey(
|
|
2750
|
+
E,
|
|
2757
2751
|
u.elapsedMs,
|
|
2758
|
-
|
|
2752
|
+
ft
|
|
2759
2753
|
);
|
|
2760
|
-
return
|
|
2761
|
-
diffPath:
|
|
2762
|
-
label:
|
|
2763
|
-
}), u.onDisplayed(
|
|
2754
|
+
return _ && u.expressionPath != null ? (m?.onBufferHit(), { usedBuffer: !1, underrun: !1, held: !1 }) : _ ? (e.blitBitmap(u.canvas, _.bitmap), f(_.mouthKey, u.expressionPath), u.playbackState.lastDrawnKey = h, u.onStatus({
|
|
2755
|
+
diffPath: _.mouthPath,
|
|
2756
|
+
label: _.label
|
|
2757
|
+
}), u.onDisplayed(h, _.mouthPath, _.label), m?.onBufferHit(), { usedBuffer: !0, underrun: !1, held: !1 }) : (m?.onBufferUnderrun(), { usedBuffer: !1, underrun: !0, held: !1 });
|
|
2764
2758
|
}
|
|
2765
2759
|
};
|
|
2766
2760
|
}
|
|
2767
|
-
const
|
|
2761
|
+
const Un = -1, kt = 1e5, Vn = /* @__PURE__ */ new Map();
|
|
2768
2762
|
async function Ui(e) {
|
|
2769
|
-
let t =
|
|
2763
|
+
let t = Vn.get(e);
|
|
2770
2764
|
if (!t) {
|
|
2771
2765
|
const n = await fetch(e);
|
|
2772
2766
|
if (!n.ok)
|
|
@@ -2774,7 +2768,7 @@ async function Ui(e) {
|
|
|
2774
2768
|
`Failed to fetch worker script (${n.status}): ${e}`
|
|
2775
2769
|
);
|
|
2776
2770
|
const r = await n.blob();
|
|
2777
|
-
t = URL.createObjectURL(r),
|
|
2771
|
+
t = URL.createObjectURL(r), Vn.set(e, t);
|
|
2778
2772
|
}
|
|
2779
2773
|
return new Worker(t, { name: "visemeDiffPreview" });
|
|
2780
2774
|
}
|
|
@@ -2786,9 +2780,9 @@ function jt(e, t) {
|
|
|
2786
2780
|
const n = e.getContext("2d");
|
|
2787
2781
|
n && n.drawImage(t, 0, 0);
|
|
2788
2782
|
}
|
|
2789
|
-
function
|
|
2783
|
+
function Wn(e, t) {
|
|
2790
2784
|
let n = 0, r = null;
|
|
2791
|
-
const s =
|
|
2785
|
+
const s = hr(async (i, a) => (await Kt(), await Gt(e, i), s.isLatestSeq(a)));
|
|
2792
2786
|
return {
|
|
2793
2787
|
usesWorker: !1,
|
|
2794
2788
|
async loadAssets(i) {
|
|
@@ -2799,7 +2793,7 @@ function Vn(e, t) {
|
|
|
2799
2793
|
return r;
|
|
2800
2794
|
},
|
|
2801
2795
|
async renderSilOnly() {
|
|
2802
|
-
n += 1, s.reset(), await
|
|
2796
|
+
n += 1, s.reset(), await vi(e);
|
|
2803
2797
|
},
|
|
2804
2798
|
drawLiveFrame(i, a, o, d) {
|
|
2805
2799
|
s.enqueue(a, o, d);
|
|
@@ -2830,201 +2824,201 @@ function Vn(e, t) {
|
|
|
2830
2824
|
}
|
|
2831
2825
|
function Wi(e, t, n) {
|
|
2832
2826
|
let r = null, s = 1, i = 0, a = !1, o = !1, d = null;
|
|
2833
|
-
const
|
|
2834
|
-
let u =
|
|
2835
|
-
const
|
|
2836
|
-
drawKey:
|
|
2837
|
-
onDisplayed:
|
|
2838
|
-
}), await
|
|
2827
|
+
const f = /* @__PURE__ */ new Map(), c = /* @__PURE__ */ new Map();
|
|
2828
|
+
let u = kt;
|
|
2829
|
+
const m = hr(async (P, p, k) => (f.set(p, {
|
|
2830
|
+
drawKey: k.drawKey,
|
|
2831
|
+
onDisplayed: k.onDisplayed
|
|
2832
|
+
}), await D(
|
|
2839
2833
|
{
|
|
2840
2834
|
type: "drawFrame",
|
|
2841
|
-
diffPath:
|
|
2842
|
-
expressionDiffPath:
|
|
2843
|
-
liveSeq:
|
|
2835
|
+
diffPath: P.mouthPath,
|
|
2836
|
+
expressionDiffPath: P.expressionPath,
|
|
2837
|
+
liveSeq: p
|
|
2844
2838
|
},
|
|
2845
2839
|
void 0,
|
|
2846
2840
|
!0
|
|
2847
|
-
), !1)),
|
|
2848
|
-
if (
|
|
2849
|
-
let
|
|
2850
|
-
for (const [
|
|
2851
|
-
|
|
2852
|
-
|
|
2841
|
+
), !1)), g = (P) => {
|
|
2842
|
+
if (P === Un) {
|
|
2843
|
+
let x = -1, R;
|
|
2844
|
+
for (const [K, B] of f)
|
|
2845
|
+
K >= x && (x = K, R = B);
|
|
2846
|
+
x >= 0 && f.delete(x), R?.onDisplayed?.(R.drawKey);
|
|
2853
2847
|
return;
|
|
2854
2848
|
}
|
|
2855
|
-
const
|
|
2856
|
-
|
|
2857
|
-
},
|
|
2858
|
-
o || !r || r.postMessage(
|
|
2859
|
-
},
|
|
2849
|
+
const p = -P, k = f.get(p);
|
|
2850
|
+
f.delete(p), k?.onDisplayed?.(k.drawKey);
|
|
2851
|
+
}, E = /* @__PURE__ */ new Map(), h = (P, p) => {
|
|
2852
|
+
o || !r || r.postMessage(P, []);
|
|
2853
|
+
}, D = (P, p, k = !1) => {
|
|
2860
2854
|
if (o) return Promise.resolve();
|
|
2861
|
-
const
|
|
2862
|
-
return new Promise((
|
|
2863
|
-
|
|
2864
|
-
resolve: (
|
|
2865
|
-
reject:
|
|
2866
|
-
generation: typeof
|
|
2867
|
-
expectRenderDone:
|
|
2868
|
-
}),
|
|
2855
|
+
const x = s++;
|
|
2856
|
+
return new Promise((R, K) => {
|
|
2857
|
+
E.set(x, {
|
|
2858
|
+
resolve: (B) => R(B),
|
|
2859
|
+
reject: K,
|
|
2860
|
+
generation: typeof P.generation == "number" ? P.generation : void 0,
|
|
2861
|
+
expectRenderDone: k
|
|
2862
|
+
}), h({ ...P, requestId: x });
|
|
2869
2863
|
});
|
|
2870
|
-
},
|
|
2871
|
-
r = await Ui(n), r.onmessage = (
|
|
2864
|
+
}, _ = (async () => {
|
|
2865
|
+
r = await Ui(n), r.onmessage = (P) => {
|
|
2872
2866
|
if (o) return;
|
|
2873
|
-
const
|
|
2874
|
-
if (
|
|
2875
|
-
t.onStatus?.(
|
|
2867
|
+
const p = P.data;
|
|
2868
|
+
if (p.type === "status") {
|
|
2869
|
+
t.onStatus?.(p.label);
|
|
2876
2870
|
return;
|
|
2877
2871
|
}
|
|
2878
|
-
if (
|
|
2879
|
-
if (
|
|
2880
|
-
const
|
|
2881
|
-
c.delete(
|
|
2872
|
+
if (p.type === "frame") {
|
|
2873
|
+
if (p.generation <= -kt) {
|
|
2874
|
+
const R = -p.generation, K = c.get(R);
|
|
2875
|
+
c.delete(R), K?.resolve(p.bitmap);
|
|
2882
2876
|
return;
|
|
2883
2877
|
}
|
|
2884
|
-
const
|
|
2885
|
-
if (!
|
|
2886
|
-
|
|
2878
|
+
const x = p.generation < 0;
|
|
2879
|
+
if (!x && p.generation !== i) {
|
|
2880
|
+
p.bitmap.close();
|
|
2887
2881
|
return;
|
|
2888
2882
|
}
|
|
2889
|
-
if (
|
|
2890
|
-
const
|
|
2891
|
-
if (!
|
|
2892
|
-
|
|
2883
|
+
if (x && !(p.generation === Un)) {
|
|
2884
|
+
const K = -p.generation;
|
|
2885
|
+
if (!m.isLatestSeq(K)) {
|
|
2886
|
+
Ve()?.onWorkerStale(), p.bitmap.close();
|
|
2893
2887
|
return;
|
|
2894
2888
|
}
|
|
2895
2889
|
}
|
|
2896
|
-
if (
|
|
2897
|
-
|
|
2890
|
+
if (x && t.shouldAcceptLiveFrame && !t.shouldAcceptLiveFrame()) {
|
|
2891
|
+
Ve()?.onWorkerStale(), p.bitmap.close();
|
|
2898
2892
|
return;
|
|
2899
2893
|
}
|
|
2900
|
-
jt(e,
|
|
2894
|
+
jt(e, p.bitmap), p.bitmap.close(), x && g(p.generation);
|
|
2901
2895
|
return;
|
|
2902
2896
|
}
|
|
2903
|
-
const
|
|
2904
|
-
if (
|
|
2905
|
-
switch (
|
|
2897
|
+
const k = E.get(p.requestId);
|
|
2898
|
+
if (k)
|
|
2899
|
+
switch (p.type) {
|
|
2906
2900
|
case "ready":
|
|
2907
|
-
|
|
2901
|
+
E.delete(p.requestId), k.resolve();
|
|
2908
2902
|
break;
|
|
2909
2903
|
case "loadAssetsDone":
|
|
2910
|
-
|
|
2904
|
+
E.delete(p.requestId), d = p.visemePaths?.length ? new Set(p.visemePaths) : null, k.resolve({ width: p.width, height: p.height, visemePaths: p.visemePaths });
|
|
2911
2905
|
break;
|
|
2912
2906
|
case "renderDone":
|
|
2913
|
-
if (
|
|
2907
|
+
if (k.expectRenderDone && k.generation != null && p.generation !== k.generation)
|
|
2914
2908
|
return;
|
|
2915
|
-
|
|
2909
|
+
E.delete(p.requestId), k.resolve();
|
|
2916
2910
|
break;
|
|
2917
2911
|
case "renderAborted":
|
|
2918
|
-
|
|
2912
|
+
E.delete(p.requestId), k.resolve();
|
|
2919
2913
|
break;
|
|
2920
2914
|
case "error":
|
|
2921
|
-
|
|
2915
|
+
E.delete(p.requestId), t.onError?.(p.message), k.reject(new Error(p.message));
|
|
2922
2916
|
break;
|
|
2923
2917
|
}
|
|
2924
|
-
}, r.onerror = (
|
|
2918
|
+
}, r.onerror = (P) => {
|
|
2925
2919
|
if (o) return;
|
|
2926
|
-
const
|
|
2927
|
-
t.onError?.(
|
|
2928
|
-
for (const [,
|
|
2929
|
-
|
|
2930
|
-
|
|
2931
|
-
}, await
|
|
2920
|
+
const p = P.message || "Worker error";
|
|
2921
|
+
t.onError?.(p);
|
|
2922
|
+
for (const [, k] of E)
|
|
2923
|
+
k.reject(new Error(p));
|
|
2924
|
+
E.clear();
|
|
2925
|
+
}, await D({ type: "init" }), a = !0;
|
|
2932
2926
|
})();
|
|
2933
2927
|
return {
|
|
2934
2928
|
usesWorker: !0,
|
|
2935
|
-
async loadAssets(
|
|
2929
|
+
async loadAssets(P) {
|
|
2936
2930
|
if (o) return { width: 842, height: 1264 };
|
|
2937
|
-
if (await
|
|
2931
|
+
if (await _, o) return { width: 842, height: 1264 };
|
|
2938
2932
|
if (!a) throw new Error("Worker init failed");
|
|
2939
|
-
return await
|
|
2933
|
+
return await D({
|
|
2940
2934
|
type: "loadAssets",
|
|
2941
|
-
keyHex:
|
|
2942
|
-
urls:
|
|
2935
|
+
keyHex: P,
|
|
2936
|
+
urls: Qr(We())
|
|
2943
2937
|
}) ?? { width: 842, height: 1264 };
|
|
2944
2938
|
},
|
|
2945
2939
|
getVisemeAtlasPaths() {
|
|
2946
2940
|
return d;
|
|
2947
2941
|
},
|
|
2948
2942
|
async renderSilOnly() {
|
|
2949
|
-
if (o || (await
|
|
2950
|
-
i += 1,
|
|
2951
|
-
const
|
|
2952
|
-
await
|
|
2953
|
-
{ type: "renderSil", generation:
|
|
2943
|
+
if (o || (await _, o)) return;
|
|
2944
|
+
i += 1, m.reset(), f.clear(), c.forEach(({ resolve: p }) => p(null)), c.clear(), u = kt;
|
|
2945
|
+
const P = i;
|
|
2946
|
+
await D({ type: "cancelLiveDraws" }), await D(
|
|
2947
|
+
{ type: "renderSil", generation: P },
|
|
2954
2948
|
void 0,
|
|
2955
2949
|
!0
|
|
2956
2950
|
);
|
|
2957
2951
|
},
|
|
2958
|
-
drawLiveFrame(
|
|
2959
|
-
o ||
|
|
2960
|
-
o ||
|
|
2952
|
+
drawLiveFrame(P, p, k, x) {
|
|
2953
|
+
o || _.then(() => {
|
|
2954
|
+
o || m.enqueue(p, k, x);
|
|
2961
2955
|
});
|
|
2962
2956
|
},
|
|
2963
|
-
compositePrefetchFrame(
|
|
2964
|
-
return o ? Promise.resolve(null) :
|
|
2957
|
+
compositePrefetchFrame(P, p) {
|
|
2958
|
+
return o ? Promise.resolve(null) : _.then(() => {
|
|
2965
2959
|
if (o) return null;
|
|
2966
|
-
const
|
|
2967
|
-
return new Promise((
|
|
2968
|
-
c.set(
|
|
2960
|
+
const k = ++u;
|
|
2961
|
+
return new Promise((x) => {
|
|
2962
|
+
c.set(k, { resolve: x }), D(
|
|
2969
2963
|
{
|
|
2970
2964
|
type: "drawFrame",
|
|
2971
|
-
diffPath:
|
|
2972
|
-
expressionDiffPath:
|
|
2973
|
-
liveSeq:
|
|
2965
|
+
diffPath: P.mouthPath,
|
|
2966
|
+
expressionDiffPath: P.expressionPath,
|
|
2967
|
+
liveSeq: k
|
|
2974
2968
|
},
|
|
2975
2969
|
void 0,
|
|
2976
2970
|
!0
|
|
2977
2971
|
).catch(() => {
|
|
2978
|
-
c.delete(
|
|
2972
|
+
c.delete(k), x(null);
|
|
2979
2973
|
});
|
|
2980
2974
|
});
|
|
2981
2975
|
});
|
|
2982
2976
|
},
|
|
2983
|
-
blitBitmap(
|
|
2984
|
-
jt(
|
|
2977
|
+
blitBitmap(P, p) {
|
|
2978
|
+
jt(P, p);
|
|
2985
2979
|
},
|
|
2986
2980
|
supportsBufferedPlayback: !0,
|
|
2987
|
-
async renderViseme(
|
|
2988
|
-
if (o || (await
|
|
2989
|
-
i += 1,
|
|
2990
|
-
const
|
|
2981
|
+
async renderViseme(P, p, k = {}) {
|
|
2982
|
+
if (o || (await _, o)) return;
|
|
2983
|
+
i += 1, m.reset(), f.clear();
|
|
2984
|
+
const x = i;
|
|
2991
2985
|
try {
|
|
2992
|
-
await
|
|
2986
|
+
await D({ type: "cancelLiveDraws" }), await D(
|
|
2993
2987
|
{
|
|
2994
2988
|
type: "renderViseme",
|
|
2995
|
-
generation:
|
|
2996
|
-
to:
|
|
2997
|
-
from:
|
|
2998
|
-
transitionDurationMs:
|
|
2999
|
-
gapMs:
|
|
3000
|
-
threshold:
|
|
2989
|
+
generation: x,
|
|
2990
|
+
to: p,
|
|
2991
|
+
from: k.from,
|
|
2992
|
+
transitionDurationMs: k.transitionDurationMs,
|
|
2993
|
+
gapMs: k.gapMs,
|
|
2994
|
+
threshold: k.threshold
|
|
3001
2995
|
},
|
|
3002
2996
|
void 0,
|
|
3003
2997
|
!0
|
|
3004
2998
|
);
|
|
3005
|
-
} catch (
|
|
3006
|
-
if (
|
|
3007
|
-
throw
|
|
2999
|
+
} catch (R) {
|
|
3000
|
+
if (R?.name === "AbortError") return;
|
|
3001
|
+
throw R;
|
|
3008
3002
|
}
|
|
3009
3003
|
},
|
|
3010
3004
|
dispose() {
|
|
3011
3005
|
if (!o) {
|
|
3012
|
-
o = !0, i += 1,
|
|
3013
|
-
for (const [,
|
|
3014
|
-
|
|
3015
|
-
|
|
3006
|
+
o = !0, i += 1, m.reset(), f.clear(), c.forEach(({ resolve: P }) => P(null)), c.clear(), u = kt;
|
|
3007
|
+
for (const [, P] of E)
|
|
3008
|
+
P.resolve();
|
|
3009
|
+
E.clear(), r?.terminate(), r = null;
|
|
3016
3010
|
}
|
|
3017
3011
|
}
|
|
3018
3012
|
};
|
|
3019
3013
|
}
|
|
3020
3014
|
function Hi(e, t = {}) {
|
|
3021
3015
|
if (!Vi())
|
|
3022
|
-
return
|
|
3016
|
+
return Wn(e, t);
|
|
3023
3017
|
const n = Rr(t.workerScriptUrl);
|
|
3024
3018
|
try {
|
|
3025
3019
|
return Wi(e, t, n);
|
|
3026
3020
|
} catch {
|
|
3027
|
-
return
|
|
3021
|
+
return Wn(e, t);
|
|
3028
3022
|
}
|
|
3029
3023
|
}
|
|
3030
3024
|
class $i extends Error {
|
|
@@ -3067,570 +3061,566 @@ const qi = {
|
|
|
3067
3061
|
fontSize: "0.875rem",
|
|
3068
3062
|
textAlign: "center"
|
|
3069
3063
|
};
|
|
3070
|
-
function
|
|
3071
|
-
return
|
|
3064
|
+
function ut(e) {
|
|
3065
|
+
return Nr(e) ? tr : er;
|
|
3072
3066
|
}
|
|
3073
|
-
function
|
|
3067
|
+
function Me(e, t) {
|
|
3074
3068
|
return t?.isSpeaking() ? t : e.isSpeaking() ? e : t?.isConnected() ? t : e;
|
|
3075
3069
|
}
|
|
3076
|
-
const na =
|
|
3070
|
+
const na = Sr(function({
|
|
3077
3071
|
id: t,
|
|
3078
3072
|
avatarId: n,
|
|
3079
3073
|
faceId: r,
|
|
3080
3074
|
assets: s,
|
|
3081
3075
|
authToken: i,
|
|
3082
3076
|
apiBase: a,
|
|
3083
|
-
ttsEngineId: o =
|
|
3077
|
+
ttsEngineId: o = Ye,
|
|
3084
3078
|
voiceId: d,
|
|
3085
|
-
speakingRate:
|
|
3079
|
+
speakingRate: f = Dt,
|
|
3086
3080
|
className: c,
|
|
3087
3081
|
style: u,
|
|
3088
|
-
canvasStyle:
|
|
3089
|
-
onStatusChange:
|
|
3090
|
-
onDisplayStatus:
|
|
3091
|
-
onError:
|
|
3092
|
-
onReady:
|
|
3093
|
-
showErrorOverlay:
|
|
3094
|
-
onUserTranscript:
|
|
3095
|
-
onBotOutput:
|
|
3096
|
-
onRealtimeLipsyncDebug:
|
|
3097
|
-
onFrameRenderStats:
|
|
3098
|
-
lipsyncBufferedPlayback:
|
|
3099
|
-
lipsyncPlaybackWarmupMs:
|
|
3100
|
-
},
|
|
3101
|
-
const
|
|
3102
|
-
|
|
3103
|
-
const
|
|
3082
|
+
canvasStyle: m,
|
|
3083
|
+
onStatusChange: g,
|
|
3084
|
+
onDisplayStatus: E,
|
|
3085
|
+
onError: h,
|
|
3086
|
+
onReady: D,
|
|
3087
|
+
showErrorOverlay: _ = !0,
|
|
3088
|
+
onUserTranscript: P,
|
|
3089
|
+
onBotOutput: p,
|
|
3090
|
+
onRealtimeLipsyncDebug: k,
|
|
3091
|
+
onFrameRenderStats: x,
|
|
3092
|
+
lipsyncBufferedPlayback: R = !0,
|
|
3093
|
+
lipsyncPlaybackWarmupMs: K = 1500
|
|
3094
|
+
}, B) {
|
|
3095
|
+
const S = L(null), b = L(null), A = L(null), ne = L(R);
|
|
3096
|
+
ne.current = R;
|
|
3097
|
+
const M = L(0), Y = L(ln()), X = L(li()), ae = L(0), Z = L(0), de = L(0), fe = L(null), me = L(null), J = L(!1), he = L(!1), G = L(!1), ie = L("sil"), w = L(0), I = L(!1), T = L(
|
|
3104
3098
|
null
|
|
3105
|
-
),
|
|
3106
|
-
|
|
3099
|
+
), U = L(!1), [F, te] = ct("idle"), [ee, j] = ct(null), [q, De] = ct(!1), [He, ke] = ct(!1), [$e, Re] = ct({ width: 842, height: 1264 }), l = L(i ?? null), v = a?.trim() || dt, O = L(null), H = L(null), oe = L(!1), Be = L({ width: 842, height: 1264 }), ce = L(null), Ce = L("sil"), ge = L(void 0), tt = L(/* @__PURE__ */ new Map()), nt = L(D), se = L(E), rt = L(h), mt = L(P), ht = L(p), be = L(k), st = L(x), Ee = L(bi());
|
|
3100
|
+
nt.current = D, se.current = E, rt.current = h, mt.current = P, ht.current = p, be.current = k, st.current = x, Le(() => {
|
|
3107
3101
|
const y = Ee.current;
|
|
3108
|
-
return
|
|
3102
|
+
return Ln(y), () => Ln(null);
|
|
3109
3103
|
}, []);
|
|
3110
|
-
const
|
|
3104
|
+
const ue = Se(
|
|
3111
3105
|
(y) => {
|
|
3112
|
-
const
|
|
3113
|
-
return { ttsEngineId:
|
|
3106
|
+
const C = y?.ttsEngineId ?? o ?? H.current?.ttsEngineId ?? Ye, N = y?.voiceId ?? d ?? H.current?.voiceId ?? ut(C);
|
|
3107
|
+
return { ttsEngineId: C, voiceId: N };
|
|
3114
3108
|
},
|
|
3115
3109
|
[o, d]
|
|
3116
|
-
), le =
|
|
3117
|
-
|
|
3118
|
-
}, []), pe =
|
|
3110
|
+
), le = Se((y) => {
|
|
3111
|
+
j(y), rt.current?.(y);
|
|
3112
|
+
}, []), pe = Se(
|
|
3119
3113
|
(y) => {
|
|
3120
|
-
|
|
3114
|
+
te(y), g?.(y);
|
|
3121
3115
|
},
|
|
3122
|
-
[
|
|
3123
|
-
),
|
|
3124
|
-
|
|
3116
|
+
[g]
|
|
3117
|
+
), z = L(
|
|
3118
|
+
In(pe, v, {
|
|
3125
3119
|
onLipsyncDebug: (y) => be.current?.(y)
|
|
3126
3120
|
})
|
|
3127
|
-
),
|
|
3128
|
-
Le(() => (
|
|
3121
|
+
), Q = L(null);
|
|
3122
|
+
Le(() => (z.current = In(
|
|
3129
3123
|
pe,
|
|
3130
3124
|
v,
|
|
3131
3125
|
{
|
|
3132
3126
|
onLipsyncDebug: (y) => be.current?.(y)
|
|
3133
3127
|
}
|
|
3134
|
-
), i &&
|
|
3135
|
-
|
|
3136
|
-
const y =
|
|
3137
|
-
y && (y.disconnect(),
|
|
3128
|
+
), i && z.current.setDeveloperToken(i), z.current.setTtsEngineId(o), () => {
|
|
3129
|
+
z.current.stop();
|
|
3130
|
+
const y = Q.current;
|
|
3131
|
+
y && (y.disconnect(), Q.current = null);
|
|
3138
3132
|
}), [pe, i, o, v]);
|
|
3139
|
-
const pt =
|
|
3133
|
+
const pt = Se(() => (Q.current || (Q.current = xs(
|
|
3140
3134
|
pe,
|
|
3141
3135
|
{
|
|
3142
|
-
speakingRate:
|
|
3143
|
-
onUserTranscript: (y,
|
|
3136
|
+
speakingRate: f,
|
|
3137
|
+
onUserTranscript: (y, C) => mt.current?.(y, C),
|
|
3144
3138
|
onBotOutput: (y) => ht.current?.(y),
|
|
3145
3139
|
onLipsyncDebug: (y) => be.current?.(y)
|
|
3146
3140
|
}
|
|
3147
|
-
),
|
|
3141
|
+
), Q.current.setTtsEngineId(o)), Q.current), [pe, f, o]), ye = Se(() => {
|
|
3148
3142
|
fe.current != null && (clearTimeout(fe.current), fe.current = null);
|
|
3149
|
-
}, []),
|
|
3150
|
-
|
|
3151
|
-
}, []), mn =
|
|
3152
|
-
!
|
|
3153
|
-
if (
|
|
3154
|
-
|
|
3155
|
-
|
|
3143
|
+
}, []), Ae = Se(() => {
|
|
3144
|
+
me.current != null && (clearTimeout(me.current), me.current = null), G.current = !1;
|
|
3145
|
+
}, []), mn = Se(() => {
|
|
3146
|
+
!U.current || !T.current || (Ae(), G.current = !0, me.current = setTimeout(() => {
|
|
3147
|
+
if (me.current = null, Me(
|
|
3148
|
+
z.current,
|
|
3149
|
+
Q.current
|
|
3156
3150
|
).isSpeaking()) {
|
|
3157
|
-
|
|
3151
|
+
G.current = !1;
|
|
3158
3152
|
return;
|
|
3159
3153
|
}
|
|
3160
|
-
if (
|
|
3161
|
-
|
|
3154
|
+
if (J.current) {
|
|
3155
|
+
G.current = !1;
|
|
3162
3156
|
return;
|
|
3163
3157
|
}
|
|
3164
|
-
const y =
|
|
3158
|
+
const y = T.current;
|
|
3165
3159
|
if (!y) {
|
|
3166
|
-
|
|
3160
|
+
G.current = !1;
|
|
3167
3161
|
return;
|
|
3168
3162
|
}
|
|
3169
3163
|
y.restart(), y.setActive(!0);
|
|
3170
|
-
const
|
|
3171
|
-
let
|
|
3172
|
-
const
|
|
3173
|
-
|
|
3174
|
-
},
|
|
3175
|
-
|
|
3164
|
+
const C = y.getVideo();
|
|
3165
|
+
let N = !1;
|
|
3166
|
+
const $ = () => {
|
|
3167
|
+
N || (N = !0, C.removeEventListener("playing", V), G.current = !1);
|
|
3168
|
+
}, V = () => {
|
|
3169
|
+
$();
|
|
3176
3170
|
};
|
|
3177
|
-
if (
|
|
3178
|
-
|
|
3171
|
+
if (C.addEventListener("playing", V, { once: !0 }), C.readyState >= HTMLMediaElement.HAVE_CURRENT_DATA && !C.paused) {
|
|
3172
|
+
$();
|
|
3179
3173
|
return;
|
|
3180
3174
|
}
|
|
3181
|
-
setTimeout(
|
|
3175
|
+
setTimeout($, 300);
|
|
3182
3176
|
}, Ei));
|
|
3183
|
-
}, [
|
|
3184
|
-
if (
|
|
3185
|
-
|
|
3177
|
+
}, [Ae]), qe = Se(() => {
|
|
3178
|
+
if (ye(), se.current?.("sil"), J.current = !1, !U.current || !T.current) {
|
|
3179
|
+
G.current = !1;
|
|
3186
3180
|
return;
|
|
3187
3181
|
}
|
|
3188
3182
|
mn();
|
|
3189
|
-
}, [
|
|
3183
|
+
}, [ye, mn]), Bt = Se(
|
|
3190
3184
|
async (y) => {
|
|
3191
|
-
const
|
|
3192
|
-
y?.fallbackOnly || (
|
|
3185
|
+
const C = Z.current, N = b.current, $ = S.current, V = () => {
|
|
3186
|
+
y?.fallbackOnly || (J.current = !1);
|
|
3193
3187
|
};
|
|
3194
|
-
if (!
|
|
3195
|
-
|
|
3188
|
+
if (!N || !$ || !q) {
|
|
3189
|
+
V();
|
|
3196
3190
|
return;
|
|
3197
3191
|
}
|
|
3198
|
-
if (
|
|
3199
|
-
|
|
3200
|
-
|
|
3192
|
+
if (Me(
|
|
3193
|
+
z.current,
|
|
3194
|
+
Q.current
|
|
3201
3195
|
).isSpeaking()) {
|
|
3202
|
-
|
|
3196
|
+
V();
|
|
3203
3197
|
return;
|
|
3204
3198
|
}
|
|
3205
3199
|
if (y?.fallbackOnly) {
|
|
3206
|
-
if (!
|
|
3207
|
-
|
|
3208
|
-
|
|
3200
|
+
if (!J.current || (ve(Y.current), await N.renderSilOnly(), C !== Z.current) || Me(
|
|
3201
|
+
z.current,
|
|
3202
|
+
Q.current
|
|
3209
3203
|
).isSpeaking())
|
|
3210
3204
|
return;
|
|
3211
|
-
|
|
3205
|
+
qe();
|
|
3212
3206
|
return;
|
|
3213
3207
|
}
|
|
3214
|
-
if (Ii(
|
|
3215
|
-
ve(
|
|
3208
|
+
if (Ii(Y.current)) {
|
|
3209
|
+
ve(Y.current), qe();
|
|
3216
3210
|
return;
|
|
3217
3211
|
}
|
|
3218
|
-
if (
|
|
3219
|
-
if (ve(
|
|
3220
|
-
|
|
3221
|
-
|
|
3212
|
+
if (ne.current && N.supportsBufferedPlayback && !y?.fallbackOnly) {
|
|
3213
|
+
if (ve(Y.current), A.current?.reset(), await N.renderSilOnly(), C !== Z.current || Me(
|
|
3214
|
+
z.current,
|
|
3215
|
+
Q.current
|
|
3222
3216
|
).isSpeaking())
|
|
3223
3217
|
return;
|
|
3224
|
-
|
|
3218
|
+
qe();
|
|
3225
3219
|
return;
|
|
3226
3220
|
}
|
|
3227
|
-
const
|
|
3228
|
-
|
|
3229
|
-
|
|
3230
|
-
|
|
3221
|
+
const _e = Di(
|
|
3222
|
+
Me(
|
|
3223
|
+
z.current,
|
|
3224
|
+
Q.current
|
|
3231
3225
|
).getVisemeQueue(),
|
|
3232
|
-
|
|
3233
|
-
|
|
3234
|
-
), wt =
|
|
3235
|
-
|
|
3236
|
-
|
|
3226
|
+
w.current,
|
|
3227
|
+
ie.current
|
|
3228
|
+
), wt = Ri(
|
|
3229
|
+
_e,
|
|
3230
|
+
ce.current
|
|
3237
3231
|
);
|
|
3238
|
-
if (ve(
|
|
3239
|
-
if (await
|
|
3240
|
-
|
|
3241
|
-
|
|
3232
|
+
if (ve(Y.current), !wt) {
|
|
3233
|
+
if (await N.renderSilOnly(), C !== Z.current || Me(
|
|
3234
|
+
z.current,
|
|
3235
|
+
Q.current
|
|
3242
3236
|
).isSpeaking())
|
|
3243
3237
|
return;
|
|
3244
|
-
|
|
3238
|
+
qe();
|
|
3245
3239
|
return;
|
|
3246
3240
|
}
|
|
3247
3241
|
try {
|
|
3248
|
-
await
|
|
3249
|
-
from:
|
|
3250
|
-
transitionDurationMs:
|
|
3242
|
+
await N.renderViseme($, "sil", {
|
|
3243
|
+
from: _e,
|
|
3244
|
+
transitionDurationMs: fr
|
|
3251
3245
|
});
|
|
3252
|
-
} catch (
|
|
3253
|
-
if (
|
|
3254
|
-
throw
|
|
3246
|
+
} catch (xe) {
|
|
3247
|
+
if (xe?.name !== "AbortError")
|
|
3248
|
+
throw xe;
|
|
3255
3249
|
}
|
|
3256
|
-
if (
|
|
3257
|
-
|
|
3250
|
+
if (C !== Z.current) {
|
|
3251
|
+
V();
|
|
3258
3252
|
return;
|
|
3259
3253
|
}
|
|
3260
|
-
if (
|
|
3261
|
-
|
|
3262
|
-
|
|
3254
|
+
if (Me(
|
|
3255
|
+
z.current,
|
|
3256
|
+
Q.current
|
|
3263
3257
|
).isSpeaking()) {
|
|
3264
|
-
|
|
3258
|
+
V();
|
|
3265
3259
|
return;
|
|
3266
3260
|
}
|
|
3267
|
-
|
|
3268
|
-
},
|
|
3269
|
-
[
|
|
3270
|
-
),
|
|
3271
|
-
if (
|
|
3272
|
-
|
|
3273
|
-
const y =
|
|
3274
|
-
|
|
3275
|
-
|
|
3261
|
+
qe();
|
|
3262
|
+
},
|
|
3263
|
+
[q, qe]
|
|
3264
|
+
), it = Se(() => {
|
|
3265
|
+
if (he.current || J.current) return;
|
|
3266
|
+
he.current = !0, J.current = !0, ye();
|
|
3267
|
+
const y = Z.current;
|
|
3268
|
+
Bt().finally(() => {
|
|
3269
|
+
he.current = !1;
|
|
3276
3270
|
}), fe.current = setTimeout(() => {
|
|
3277
|
-
fe.current = null, y ===
|
|
3278
|
-
},
|
|
3279
|
-
}, [
|
|
3271
|
+
fe.current = null, y === Z.current && Bt({ fallbackOnly: !0 });
|
|
3272
|
+
}, Bi());
|
|
3273
|
+
}, [ye, Bt]), hn = Se(async () => {
|
|
3280
3274
|
const y = Math.floor(Date.now() / 1e3);
|
|
3281
|
-
if (
|
|
3282
|
-
return
|
|
3283
|
-
const
|
|
3284
|
-
l.current =
|
|
3285
|
-
const
|
|
3286
|
-
return
|
|
3287
|
-
key:
|
|
3288
|
-
expiresAt:
|
|
3289
|
-
},
|
|
3275
|
+
if (O.current && y < O.current.expiresAt - 60)
|
|
3276
|
+
return O.current.key;
|
|
3277
|
+
const C = l.current ?? await Lt();
|
|
3278
|
+
l.current = C, z.current.setDeveloperToken(C);
|
|
3279
|
+
const N = await Kr(C, v);
|
|
3280
|
+
return O.current = {
|
|
3281
|
+
key: N.value,
|
|
3282
|
+
expiresAt: N.expiresAt
|
|
3283
|
+
}, N.value;
|
|
3290
3284
|
}, [v]);
|
|
3291
3285
|
Le(() => {
|
|
3292
|
-
i && (l.current = i,
|
|
3286
|
+
i && (l.current = i, z.current.setDeveloperToken(i));
|
|
3293
3287
|
}, [i]), Le(() => {
|
|
3294
|
-
|
|
3288
|
+
z.current.setTtsEngineId(o), Q.current?.setTtsEngineId(o), H.current && (H.current.ttsEngineId = o);
|
|
3295
3289
|
}, [o]), Le(() => {
|
|
3296
|
-
const y = d ??
|
|
3297
|
-
|
|
3290
|
+
const y = d ?? ut(o);
|
|
3291
|
+
H.current && (H.current.voiceId = y);
|
|
3298
3292
|
}, [d, o]);
|
|
3299
|
-
const
|
|
3300
|
-
() =>
|
|
3293
|
+
const Fe = _n(
|
|
3294
|
+
() => Yr(n, r),
|
|
3301
3295
|
[n, r]
|
|
3302
|
-
),
|
|
3296
|
+
), pr = _n(() => s ? JSON.stringify(s) : Fe ? `face:${Fe}` : `id:${t ?? ""}`, [s, Fe, t]);
|
|
3303
3297
|
return Le(() => {
|
|
3304
|
-
if (!t && !s && !
|
|
3298
|
+
if (!t && !s && !Fe) {
|
|
3305
3299
|
le("AiTwin requires `assets`, `avatarId`/`faceId`, or `id`");
|
|
3306
3300
|
return;
|
|
3307
3301
|
}
|
|
3308
3302
|
let y = !1;
|
|
3309
|
-
|
|
3310
|
-
const
|
|
3311
|
-
if (!
|
|
3312
|
-
let
|
|
3303
|
+
oe.current = !1, De(!1), ke(!1), j(null), H.current = null, T.current = null, U.current = !1;
|
|
3304
|
+
const C = S.current;
|
|
3305
|
+
if (!C) return;
|
|
3306
|
+
let N = null;
|
|
3313
3307
|
return (async () => {
|
|
3314
3308
|
try {
|
|
3315
|
-
let
|
|
3309
|
+
let $, V, we, _e;
|
|
3316
3310
|
if (s)
|
|
3317
|
-
|
|
3318
|
-
else if (
|
|
3319
|
-
se.current?.("loadFace"),
|
|
3311
|
+
$ = s, V = o, we = d ?? ut(V);
|
|
3312
|
+
else if (Fe)
|
|
3313
|
+
se.current?.("loadFace"), $ = kn(Fe), V = o, we = d ?? ut(V);
|
|
3320
3314
|
else {
|
|
3321
3315
|
se.current?.("getAiTwin");
|
|
3322
|
-
const
|
|
3323
|
-
|
|
3316
|
+
const W = await Ut(
|
|
3317
|
+
Ur(t),
|
|
3324
3318
|
3e4,
|
|
3325
3319
|
"getAiTwin"
|
|
3326
3320
|
);
|
|
3327
3321
|
if (y) return;
|
|
3328
|
-
if (
|
|
3322
|
+
if (!W.faceId?.trim())
|
|
3329
3323
|
throw new Error("getAiTwin returned no faceId");
|
|
3330
|
-
|
|
3324
|
+
V = W.ttsEngineId, we = d ?? W.voiceId ?? ut(V), _e = W.knowledgeContextId?.trim() || void 0, $ = kn(W.faceId);
|
|
3331
3325
|
}
|
|
3332
|
-
|
|
3333
|
-
onStatus: (
|
|
3334
|
-
y || se.current?.(
|
|
3326
|
+
H.current = { ttsEngineId: V, voiceId: we, personaId: _e }, Jr($), T.current = fi(), N = Hi(C, {
|
|
3327
|
+
onStatus: (W) => {
|
|
3328
|
+
y || se.current?.(W);
|
|
3335
3329
|
},
|
|
3336
|
-
onError: (
|
|
3337
|
-
y || le(
|
|
3330
|
+
onError: (W) => {
|
|
3331
|
+
y || le(W);
|
|
3338
3332
|
},
|
|
3339
|
-
shouldAcceptLiveFrame: () =>
|
|
3340
|
-
|
|
3341
|
-
|
|
3342
|
-
).isSpeaking() && !
|
|
3343
|
-
}),
|
|
3344
|
-
const
|
|
3345
|
-
|
|
3333
|
+
shouldAcceptLiveFrame: () => Me(
|
|
3334
|
+
z.current,
|
|
3335
|
+
Q.current
|
|
3336
|
+
).isSpeaking() && !J.current
|
|
3337
|
+
}), b.current = N, A.current = Oi(N), ((W) => {
|
|
3338
|
+
const re = () => W && R && (b.current?.supportsBufferedPlayback ?? !1) && K > 0;
|
|
3339
|
+
z.current.setLipsyncWarmupHold(W, re), Q.current?.setLipsyncWarmupHold(W, re);
|
|
3346
3340
|
})(!0), se.current?.("auth");
|
|
3347
|
-
const
|
|
3341
|
+
const xe = l.current ?? i ?? await Ut(Lt(), 3e4, "getAuthToken");
|
|
3348
3342
|
if (y) return;
|
|
3349
|
-
l.current =
|
|
3350
|
-
const
|
|
3343
|
+
l.current = xe, z.current.setDeveloperToken(xe), z.current.setTtsEngineId(V);
|
|
3344
|
+
const at = Pt() ? await hn() : void 0;
|
|
3351
3345
|
if (y) return;
|
|
3352
3346
|
se.current?.("loadAssets");
|
|
3353
|
-
const
|
|
3354
|
-
|
|
3347
|
+
const Ke = await Ut(
|
|
3348
|
+
N.loadAssets(at),
|
|
3355
3349
|
18e4,
|
|
3356
3350
|
"load face assets"
|
|
3357
3351
|
);
|
|
3358
|
-
if (!y &&
|
|
3359
|
-
|
|
3360
|
-
requestAnimationFrame(() => {
|
|
3361
|
-
tt.current?.();
|
|
3362
|
-
});
|
|
3363
|
-
}), V.renderSilOnly().then(() => {
|
|
3352
|
+
if (!y && Ke.width > 0 && Ke.height > 0 && (Be.current = Ke, Re(Ke)), y) return;
|
|
3353
|
+
ce.current = N.getVisemeAtlasPaths(), oe.current = !0, De(!0), nt.current?.(), N.renderSilOnly().then(() => {
|
|
3364
3354
|
y || se.current?.("sil");
|
|
3365
3355
|
}), (async () => {
|
|
3366
3356
|
try {
|
|
3367
|
-
const
|
|
3368
|
-
if (await
|
|
3369
|
-
|
|
3370
|
-
const
|
|
3371
|
-
await
|
|
3372
|
-
|
|
3373
|
-
|
|
3357
|
+
const W = await Hs(at);
|
|
3358
|
+
if (await T.current.load(W), y) return;
|
|
3359
|
+
U.current = !0, ke(!0), ve(Y.current), T.current.setActive(!0);
|
|
3360
|
+
const re = T.current.getVideo();
|
|
3361
|
+
await Fn(
|
|
3362
|
+
C,
|
|
3363
|
+
re,
|
|
3374
3364
|
null,
|
|
3375
3365
|
void 0,
|
|
3376
|
-
|
|
3366
|
+
Be.current
|
|
3377
3367
|
), y || se.current?.("idle");
|
|
3378
|
-
} catch (
|
|
3368
|
+
} catch (W) {
|
|
3379
3369
|
if (y) return;
|
|
3380
|
-
|
|
3370
|
+
U.current = !1, ke(!1), console.warn("[AiTwin] Idle video unavailable:", W);
|
|
3381
3371
|
}
|
|
3382
3372
|
})();
|
|
3383
|
-
} catch (
|
|
3373
|
+
} catch ($) {
|
|
3384
3374
|
if (y) return;
|
|
3385
|
-
if (
|
|
3386
|
-
le(
|
|
3375
|
+
if ($ instanceof Vt) {
|
|
3376
|
+
le($.message);
|
|
3387
3377
|
return;
|
|
3388
3378
|
}
|
|
3389
|
-
le(
|
|
3379
|
+
le($ instanceof Error ? $.message : "Failed to load AI twin");
|
|
3390
3380
|
}
|
|
3391
3381
|
})(), () => {
|
|
3392
|
-
y = !0,
|
|
3382
|
+
y = !0, T.current?.dispose(), N?.dispose(), b.current = null;
|
|
3393
3383
|
};
|
|
3394
|
-
}, [
|
|
3395
|
-
const y = { current: !1 },
|
|
3396
|
-
const
|
|
3397
|
-
|
|
3398
|
-
|
|
3384
|
+
}, [pr, s, Fe, t, o, d, i, hn, le]), Le(() => {
|
|
3385
|
+
const y = { current: !1 }, C = () => {
|
|
3386
|
+
const N = S.current, $ = b.current, V = Me(
|
|
3387
|
+
z.current,
|
|
3388
|
+
Q.current
|
|
3399
3389
|
);
|
|
3400
|
-
if (!
|
|
3401
|
-
|
|
3390
|
+
if (!N || !$ || !q) {
|
|
3391
|
+
ae.current = requestAnimationFrame(C);
|
|
3402
3392
|
return;
|
|
3403
3393
|
}
|
|
3404
|
-
const
|
|
3405
|
-
wt && (
|
|
3406
|
-
const
|
|
3407
|
-
if (
|
|
3408
|
-
|
|
3409
|
-
const
|
|
3410
|
-
|
|
3411
|
-
const
|
|
3412
|
-
queue:
|
|
3394
|
+
const we = V.isSpeaking(), _e = V.isWarmingUp(), wt = we && !I.current, xe = I.current && !we;
|
|
3395
|
+
wt && (ye(), Ae(), J.current = !1, he.current = !1, ve(Y.current), (A.current?.getBufferedFrameCount() ?? 0) === 0 && A.current?.reset(), Ee.current.reset(), ge.current = void 0, de.current = 0, ie.current = "sil", w.current = 0, T.current?.setActive(!1)), xe && (X.current.reset(), T.current?.setActive(!1), it());
|
|
3396
|
+
const at = xe || J.current || G.current, Ke = R && $.supportsBufferedPlayback;
|
|
3397
|
+
if (_e && Ke && A.current) {
|
|
3398
|
+
U.current && T.current?.setActive(!1);
|
|
3399
|
+
const W = V.getVisemeQueue();
|
|
3400
|
+
W.length > 0 && M.current === 0 && (M.current = performance.now()), X.current.advance(performance.now());
|
|
3401
|
+
const re = X.current.getExpressionPath(), Te = X.current.getDrawKey(), Ie = {
|
|
3402
|
+
queue: W,
|
|
3413
3403
|
elapsedMs: 0,
|
|
3414
|
-
expressionPath:
|
|
3404
|
+
expressionPath: re,
|
|
3415
3405
|
expressionDrawKey: Te,
|
|
3416
|
-
availablePaths:
|
|
3406
|
+
availablePaths: ce.current
|
|
3417
3407
|
};
|
|
3418
|
-
|
|
3419
|
-
const Pe =
|
|
3420
|
-
|
|
3421
|
-
|
|
3422
|
-
),
|
|
3408
|
+
A.current.warmupTick(Ie);
|
|
3409
|
+
const Pe = A.current.isWarmupReady(
|
|
3410
|
+
Ie,
|
|
3411
|
+
K
|
|
3412
|
+
), Ge = M.current > 0 && performance.now() - M.current > Cr;
|
|
3423
3413
|
se.current?.(
|
|
3424
3414
|
Pe ? "buffer ready" : "buffering lipsync…"
|
|
3425
|
-
), (Pe ||
|
|
3415
|
+
), (Pe || Ge) && (M.current = 0, V.releaseWarmupHold()), I.current = V.isSpeaking(), ae.current = requestAnimationFrame(C);
|
|
3426
3416
|
return;
|
|
3427
3417
|
}
|
|
3428
|
-
if (
|
|
3429
|
-
|
|
3430
|
-
const
|
|
3431
|
-
Es(
|
|
3432
|
-
const Te =
|
|
3433
|
-
Te !== "sil" && (
|
|
3434
|
-
const
|
|
3435
|
-
|
|
3436
|
-
|
|
3437
|
-
|
|
3438
|
-
|
|
3418
|
+
if (we) {
|
|
3419
|
+
U.current && T.current?.setActive(!1);
|
|
3420
|
+
const W = V.getVisemeQueue(), re = V.getPlaybackElapsedMs();
|
|
3421
|
+
Es(W, re), w.current = re;
|
|
3422
|
+
const Te = W.length > 0 ? Mt(W, re) : "sil";
|
|
3423
|
+
Te !== "sil" && (ie.current = Te);
|
|
3424
|
+
const Ie = pi(
|
|
3425
|
+
re,
|
|
3426
|
+
V.getSentenceEmotions(),
|
|
3427
|
+
V.getWordQueue(),
|
|
3428
|
+
V.getStreamMood()
|
|
3439
3429
|
);
|
|
3440
|
-
|
|
3430
|
+
X.current.setTargetEmotion(Ie), X.current.setTargetEyebrow(
|
|
3441
3431
|
ui(
|
|
3442
|
-
|
|
3443
|
-
|
|
3444
|
-
an(
|
|
3432
|
+
re,
|
|
3433
|
+
V.getWordQueue(),
|
|
3434
|
+
an(Ie)
|
|
3445
3435
|
)
|
|
3446
|
-
),
|
|
3447
|
-
const Pe =
|
|
3436
|
+
), X.current.advance(performance.now());
|
|
3437
|
+
const Pe = X.current.getExpressionPath(), Ge = X.current.getDrawKey(), wr = (je, Ct, ot, xt) => {
|
|
3448
3438
|
const gn = {
|
|
3449
3439
|
label: Ce.current,
|
|
3450
|
-
elapsedMs:
|
|
3440
|
+
elapsedMs: re,
|
|
3451
3441
|
mouthPath: Ct.mouthPath,
|
|
3452
|
-
transitionMeta:
|
|
3442
|
+
transitionMeta: ge.current
|
|
3453
3443
|
};
|
|
3454
|
-
|
|
3455
|
-
|
|
3444
|
+
tt.current.set(ot, gn), A.current?.markExternallyDisplayed(
|
|
3445
|
+
ot,
|
|
3456
3446
|
Pe
|
|
3457
|
-
),
|
|
3458
|
-
const
|
|
3459
|
-
|
|
3460
|
-
|
|
3461
|
-
|
|
3462
|
-
),
|
|
3447
|
+
), $.drawLiveFrame(je, Ct, ot, (gt) => {
|
|
3448
|
+
const yr = tt.current.get(gt) ?? gn;
|
|
3449
|
+
tt.current.delete(gt), Ee.current.onDrawDisplayed(
|
|
3450
|
+
yr,
|
|
3451
|
+
W
|
|
3452
|
+
), A.current?.markExternallyDisplayed(
|
|
3463
3453
|
gt,
|
|
3464
3454
|
Pe
|
|
3465
|
-
),
|
|
3455
|
+
), xt?.(gt);
|
|
3466
3456
|
});
|
|
3467
|
-
}, pn = (
|
|
3468
|
-
Ce.current =
|
|
3469
|
-
},
|
|
3457
|
+
}, pn = (je) => {
|
|
3458
|
+
Ce.current = je.label, ge.current = je.transitionMeta, se.current?.(je.label);
|
|
3459
|
+
}, gr = R && $.supportsBufferedPlayback;
|
|
3470
3460
|
let wn = !1;
|
|
3471
|
-
|
|
3472
|
-
canvas:
|
|
3473
|
-
queue:
|
|
3474
|
-
elapsedMs:
|
|
3461
|
+
gr && A.current && (wn = A.current.tick({
|
|
3462
|
+
canvas: N,
|
|
3463
|
+
queue: W,
|
|
3464
|
+
elapsedMs: re,
|
|
3475
3465
|
expressionPath: Pe,
|
|
3476
|
-
expressionDrawKey:
|
|
3477
|
-
playbackState:
|
|
3478
|
-
availablePaths:
|
|
3466
|
+
expressionDrawKey: Ge,
|
|
3467
|
+
playbackState: Y.current,
|
|
3468
|
+
availablePaths: ce.current,
|
|
3479
3469
|
onStatus: pn,
|
|
3480
|
-
onDisplayed: (Ct,
|
|
3470
|
+
onDisplayed: (Ct, ot, xt) => {
|
|
3481
3471
|
Ee.current.onDrawDisplayed(
|
|
3482
3472
|
{
|
|
3483
|
-
label:
|
|
3484
|
-
elapsedMs:
|
|
3485
|
-
mouthPath:
|
|
3486
|
-
transitionMeta:
|
|
3473
|
+
label: xt,
|
|
3474
|
+
elapsedMs: re,
|
|
3475
|
+
mouthPath: ot,
|
|
3476
|
+
transitionMeta: ge.current
|
|
3487
3477
|
},
|
|
3488
|
-
|
|
3478
|
+
W
|
|
3489
3479
|
);
|
|
3490
3480
|
}
|
|
3491
3481
|
}).usedBuffer), wn || Ci(
|
|
3492
|
-
|
|
3493
|
-
|
|
3494
|
-
|
|
3482
|
+
N,
|
|
3483
|
+
W,
|
|
3484
|
+
re,
|
|
3495
3485
|
Pe,
|
|
3496
|
-
|
|
3497
|
-
|
|
3498
|
-
|
|
3486
|
+
Ge,
|
|
3487
|
+
Y.current,
|
|
3488
|
+
wr,
|
|
3499
3489
|
pn,
|
|
3500
|
-
|
|
3501
|
-
), Ee.current.onRafTickSpeaking(),
|
|
3502
|
-
Ee.current.snapshot(
|
|
3490
|
+
ce.current
|
|
3491
|
+
), Ee.current.onRafTickSpeaking(), st.current?.(
|
|
3492
|
+
Ee.current.snapshot(W, re)
|
|
3503
3493
|
);
|
|
3504
|
-
} else if (!
|
|
3505
|
-
const
|
|
3506
|
-
|
|
3507
|
-
|
|
3508
|
-
|
|
3494
|
+
} else if (!at && U.current && T.current) {
|
|
3495
|
+
const W = T.current, re = W.getVideo();
|
|
3496
|
+
re.readyState >= HTMLMediaElement.HAVE_CURRENT_DATA ? (W.setActive(!0), y.current || (y.current = !0, Fn(
|
|
3497
|
+
N,
|
|
3498
|
+
re,
|
|
3509
3499
|
null,
|
|
3510
3500
|
void 0,
|
|
3511
|
-
|
|
3512
|
-
() => !
|
|
3501
|
+
Be.current,
|
|
3502
|
+
() => !V.isSpeaking() && !J.current && !G.current
|
|
3513
3503
|
).then(() => se.current?.("idle")).finally(() => {
|
|
3514
3504
|
y.current = !1;
|
|
3515
|
-
}))) :
|
|
3516
|
-
|
|
3505
|
+
}))) : On(
|
|
3506
|
+
N,
|
|
3517
3507
|
null,
|
|
3518
3508
|
"__sil__",
|
|
3519
|
-
|
|
3520
|
-
(Te,
|
|
3509
|
+
Y.current,
|
|
3510
|
+
(Te, Ie, Pe, Ge) => $.drawLiveFrame(Te, Ie, Pe, Ge),
|
|
3521
3511
|
(Te) => se.current?.(Te)
|
|
3522
3512
|
);
|
|
3523
|
-
} else
|
|
3524
|
-
|
|
3513
|
+
} else at || On(
|
|
3514
|
+
N,
|
|
3525
3515
|
null,
|
|
3526
3516
|
"__sil__",
|
|
3527
|
-
|
|
3528
|
-
(
|
|
3529
|
-
(
|
|
3517
|
+
Y.current,
|
|
3518
|
+
(W, re, Te, Ie) => $.drawLiveFrame(W, re, Te, Ie),
|
|
3519
|
+
(W) => se.current?.(W)
|
|
3530
3520
|
);
|
|
3531
|
-
|
|
3521
|
+
I.current = we, ae.current = requestAnimationFrame(C);
|
|
3532
3522
|
};
|
|
3533
|
-
return
|
|
3534
|
-
cancelAnimationFrame(
|
|
3523
|
+
return ae.current = requestAnimationFrame(C), () => {
|
|
3524
|
+
cancelAnimationFrame(ae.current), ye(), Ae(), z.current.stop(), Q.current?.stop();
|
|
3535
3525
|
};
|
|
3536
3526
|
}, [
|
|
3537
|
-
|
|
3538
|
-
|
|
3539
|
-
|
|
3540
|
-
|
|
3541
|
-
|
|
3542
|
-
]),
|
|
3543
|
-
|
|
3527
|
+
q,
|
|
3528
|
+
He,
|
|
3529
|
+
it,
|
|
3530
|
+
ye,
|
|
3531
|
+
Ae
|
|
3532
|
+
]), vr(
|
|
3533
|
+
B,
|
|
3544
3534
|
() => ({
|
|
3545
|
-
speakText: async (y,
|
|
3546
|
-
const
|
|
3547
|
-
if (!
|
|
3548
|
-
const
|
|
3549
|
-
if (
|
|
3535
|
+
speakText: async (y, C) => {
|
|
3536
|
+
const N = y.trim();
|
|
3537
|
+
if (!N) return;
|
|
3538
|
+
const $ = b.current;
|
|
3539
|
+
if (!$ || !oe.current && !q)
|
|
3550
3540
|
throw new Error("AI twin is not ready");
|
|
3551
|
-
const { ttsEngineId:
|
|
3552
|
-
|
|
3541
|
+
const { ttsEngineId: V, voiceId: we } = ue(C);
|
|
3542
|
+
j(null), Z.current += 1, ye(), Ae(), J.current = !1, he.current = !1, ie.current = "sil", w.current = 0, ve(Y.current), X.current.reset(), I.current = !1;
|
|
3553
3543
|
try {
|
|
3554
|
-
|
|
3555
|
-
voiceId:
|
|
3556
|
-
speakingRate:
|
|
3557
|
-
ttsEngineId:
|
|
3544
|
+
U.current ? (T.current?.setActive(!1), T.current?.restart(), ve(Y.current)) : await $.renderSilOnly(), await z.current.speak(N, {
|
|
3545
|
+
voiceId: we,
|
|
3546
|
+
speakingRate: C?.speakingRate ?? f,
|
|
3547
|
+
ttsEngineId: V
|
|
3558
3548
|
});
|
|
3559
|
-
} catch (
|
|
3560
|
-
throw le(
|
|
3549
|
+
} catch (_e) {
|
|
3550
|
+
throw le(_e instanceof Error ? _e.message : "TTS failed"), _e;
|
|
3561
3551
|
}
|
|
3562
3552
|
},
|
|
3563
3553
|
stop: () => {
|
|
3564
|
-
|
|
3554
|
+
Z.current += 1, ye(), Ae(), J.current = !1, he.current = !1, z.current.stop(), Q.current?.stop(), ve(Y.current), A.current?.reset(), M.current = 0, I.current = !1, it();
|
|
3565
3555
|
},
|
|
3566
3556
|
setTtsEngineId: (y) => {
|
|
3567
|
-
|
|
3557
|
+
z.current.setTtsEngineId(y), Q.current?.setTtsEngineId(y), H.current && (H.current.ttsEngineId = y);
|
|
3568
3558
|
},
|
|
3569
|
-
renderViseme: async (y,
|
|
3570
|
-
const
|
|
3571
|
-
if (!
|
|
3559
|
+
renderViseme: async (y, C) => {
|
|
3560
|
+
const N = b.current, $ = S.current;
|
|
3561
|
+
if (!N || !$ || !oe.current)
|
|
3572
3562
|
throw new Error("AI twin is not ready");
|
|
3573
|
-
await
|
|
3574
|
-
from:
|
|
3575
|
-
transitionDurationMs:
|
|
3576
|
-
gapMs:
|
|
3577
|
-
onStatus: (
|
|
3563
|
+
await N.renderViseme($, y, {
|
|
3564
|
+
from: C?.from,
|
|
3565
|
+
transitionDurationMs: C?.transitionDurationMs,
|
|
3566
|
+
gapMs: C?.gapMs,
|
|
3567
|
+
onStatus: (V) => se.current?.(V)
|
|
3578
3568
|
});
|
|
3579
3569
|
},
|
|
3580
|
-
isReady: () =>
|
|
3581
|
-
getStatus: () =>
|
|
3570
|
+
isReady: () => oe.current,
|
|
3571
|
+
getStatus: () => F,
|
|
3582
3572
|
connect: async (y = {}) => {
|
|
3583
|
-
|
|
3573
|
+
j(null);
|
|
3584
3574
|
try {
|
|
3585
|
-
let
|
|
3586
|
-
|
|
3587
|
-
const
|
|
3588
|
-
await
|
|
3575
|
+
let C = y.authToken?.trim();
|
|
3576
|
+
C || (C = l.current ?? i ?? await Lt(), l.current = C);
|
|
3577
|
+
const N = y.voiceId?.trim() ?? d ?? H.current?.voiceId, $ = y.personaId?.trim() ?? H.current?.personaId, V = pt();
|
|
3578
|
+
await V.unlockAudio(), await V.connect({
|
|
3589
3579
|
...y,
|
|
3590
3580
|
apiBase: y.apiBase?.trim() || v,
|
|
3591
|
-
authToken:
|
|
3592
|
-
voiceId:
|
|
3593
|
-
personaId:
|
|
3594
|
-
speakingRate: y.speakingRate ??
|
|
3581
|
+
authToken: C,
|
|
3582
|
+
voiceId: N,
|
|
3583
|
+
personaId: $,
|
|
3584
|
+
speakingRate: y.speakingRate ?? f
|
|
3595
3585
|
});
|
|
3596
|
-
} catch (
|
|
3586
|
+
} catch (C) {
|
|
3597
3587
|
throw le(
|
|
3598
|
-
|
|
3599
|
-
),
|
|
3588
|
+
C instanceof Error ? C.message : "Voice connect failed"
|
|
3589
|
+
), C;
|
|
3600
3590
|
}
|
|
3601
3591
|
},
|
|
3602
3592
|
disconnect: async () => {
|
|
3603
|
-
const y =
|
|
3604
|
-
y && (
|
|
3593
|
+
const y = Q.current;
|
|
3594
|
+
y && (Z.current += 1, ye(), Ae(), J.current = !1, he.current = !1, ve(Y.current), A.current?.reset(), M.current = 0, I.current = !1, await y.disconnect(), it());
|
|
3605
3595
|
},
|
|
3606
|
-
isConnected: () =>
|
|
3607
|
-
getVoiceStream: () =>
|
|
3596
|
+
isConnected: () => Q.current?.isConnected() ?? !1,
|
|
3597
|
+
getVoiceStream: () => Q.current?.getVoiceStream() ?? z.current?.getVoiceStream() ?? null
|
|
3608
3598
|
}),
|
|
3609
3599
|
[
|
|
3610
|
-
|
|
3611
|
-
|
|
3600
|
+
q,
|
|
3601
|
+
f,
|
|
3612
3602
|
i,
|
|
3613
3603
|
d,
|
|
3614
|
-
|
|
3615
|
-
|
|
3616
|
-
|
|
3604
|
+
ye,
|
|
3605
|
+
Ae,
|
|
3606
|
+
it,
|
|
3617
3607
|
le,
|
|
3618
|
-
|
|
3608
|
+
ue,
|
|
3619
3609
|
pt,
|
|
3620
|
-
|
|
3610
|
+
F
|
|
3621
3611
|
]
|
|
3622
|
-
), /* @__PURE__ */
|
|
3612
|
+
), /* @__PURE__ */ _r("div", { className: c, style: { ...qi, ...u }, children: [
|
|
3623
3613
|
/* @__PURE__ */ yn(
|
|
3624
3614
|
"canvas",
|
|
3625
3615
|
{
|
|
3626
|
-
ref:
|
|
3627
|
-
width:
|
|
3628
|
-
height:
|
|
3629
|
-
style: { ...Ki, ...
|
|
3616
|
+
ref: S,
|
|
3617
|
+
width: $e.width,
|
|
3618
|
+
height: $e.height,
|
|
3619
|
+
style: { ...Ki, ...m },
|
|
3630
3620
|
"aria-label": t ? `AI twin ${t}` : "AI twin face"
|
|
3631
3621
|
}
|
|
3632
3622
|
),
|
|
3633
|
-
|
|
3623
|
+
_ && ee ? /* @__PURE__ */ yn("div", { style: Gi, children: ee }) : null
|
|
3634
3624
|
] });
|
|
3635
3625
|
}), ji = "thumbnail.webp";
|
|
3636
3626
|
function ra(e, t = zt) {
|
|
@@ -3654,31 +3644,31 @@ export {
|
|
|
3654
3644
|
ji as AI_TWIN_THUMBNAIL_FILENAME,
|
|
3655
3645
|
na as AiTwin,
|
|
3656
3646
|
Vt as AiTwinNotFoundError,
|
|
3657
|
-
|
|
3658
|
-
|
|
3659
|
-
|
|
3660
|
-
|
|
3647
|
+
Ye as DEFAULT_TTS_ENGINE_ID,
|
|
3648
|
+
nr as MIC_SAMPLE_RATE,
|
|
3649
|
+
rs as OCULUS_VISEME_IDS,
|
|
3650
|
+
rr as PLAYBACK_SAMPLE_RATE,
|
|
3661
3651
|
en as SPEAKING_RATE_MAX,
|
|
3662
3652
|
Zt as SPEAKING_RATE_MIN,
|
|
3663
|
-
|
|
3664
|
-
|
|
3653
|
+
Ze as TTS_ENGINE_CARTESIA,
|
|
3654
|
+
$n as TTS_ENGINE_GOOGLE,
|
|
3665
3655
|
Jt as TTS_ENGINE_INWORLD,
|
|
3666
3656
|
ta as VISEME_IDS,
|
|
3667
|
-
|
|
3668
|
-
|
|
3669
|
-
|
|
3657
|
+
tr as VISEME_TEST_CARTESIA_VOICE_ID,
|
|
3658
|
+
Dt as VISEME_TEST_SPEAKING_RATE,
|
|
3659
|
+
er as VISEME_TEST_VOICE_ID,
|
|
3670
3660
|
Yi as aiTwinSourceFilename,
|
|
3671
|
-
|
|
3672
|
-
|
|
3673
|
-
|
|
3674
|
-
|
|
3675
|
-
|
|
3676
|
-
|
|
3661
|
+
Rs as buildVoiceWebSocketUrl,
|
|
3662
|
+
In as createAvatarTtsLipsyncController,
|
|
3663
|
+
xs as createRealtimeVoiceLipsyncController,
|
|
3664
|
+
kn as faceAssetUrls,
|
|
3665
|
+
Ur as fetchAiTwin,
|
|
3666
|
+
Lt as fetchDevAuthToken,
|
|
3677
3667
|
sa as getAiTwinSourceUrl,
|
|
3678
3668
|
ra as getAiTwinThumbnailUrl,
|
|
3679
|
-
|
|
3680
|
-
|
|
3681
|
-
|
|
3669
|
+
is as normalizeOculusViseme,
|
|
3670
|
+
Yr as resolveDirectFaceId,
|
|
3671
|
+
Mt as resolveVisemeAtTime,
|
|
3682
3672
|
ea as resolveWordAtTime,
|
|
3683
|
-
|
|
3673
|
+
Jr as setActiveTwinAssets
|
|
3684
3674
|
};
|