@streamoji/avatar-widget 0.2.2 → 0.2.4
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/avatar-widget.cjs +5 -5
- package/dist/avatar-widget.cjs.map +1 -1
- package/dist/avatar-widget.css +1 -1
- package/dist/avatar-widget.js +652 -574
- package/dist/avatar-widget.js.map +1 -1
- package/dist/avatar-widget.umd.css +1 -1
- package/dist/avatar-widget.umd.js +52 -52
- package/dist/avatar-widget.umd.js.map +1 -1
- package/package.json +1 -1
package/dist/avatar-widget.js
CHANGED
|
@@ -1,96 +1,96 @@
|
|
|
1
|
-
import { jsx as
|
|
2
|
-
import { useGLTF as
|
|
3
|
-
import { useFrame as
|
|
4
|
-
import { memo as
|
|
1
|
+
import { jsx as c, jsxs as ie } from "react/jsx-runtime";
|
|
2
|
+
import { useGLTF as Ze, Environment as Ct } from "@react-three/drei";
|
|
3
|
+
import { useFrame as Dt, Canvas as Ot, useThree as Ft } from "@react-three/fiber";
|
|
4
|
+
import { memo as Ut, useMemo as tt, useRef as o, useState as k, useEffect as H, useCallback as $e, useLayoutEffect as Nt, Suspense as Wt } from "react";
|
|
5
5
|
import * as Fe from "three";
|
|
6
|
-
import { GLTFLoader as
|
|
7
|
-
const
|
|
8
|
-
},
|
|
9
|
-
},
|
|
10
|
-
const
|
|
11
|
-
return
|
|
12
|
-
const p =
|
|
6
|
+
import { GLTFLoader as Bt } from "three/examples/jsm/loaders/GLTFLoader.js";
|
|
7
|
+
const W = (...d) => {
|
|
8
|
+
}, Pt = (...d) => {
|
|
9
|
+
}, ft = ({ analyser: d }) => {
|
|
10
|
+
const A = o(null), v = o(null);
|
|
11
|
+
return H(() => {
|
|
12
|
+
const p = A.current;
|
|
13
13
|
if (!p) return;
|
|
14
|
-
const
|
|
15
|
-
if (!
|
|
16
|
-
let
|
|
17
|
-
|
|
18
|
-
const
|
|
19
|
-
|
|
20
|
-
const
|
|
21
|
-
if (
|
|
22
|
-
const
|
|
23
|
-
|
|
24
|
-
const
|
|
25
|
-
(!
|
|
26
|
-
const
|
|
27
|
-
|
|
28
|
-
const
|
|
14
|
+
const U = p.getContext("2d", { alpha: !0 });
|
|
15
|
+
if (!U) return;
|
|
16
|
+
let I, R = null;
|
|
17
|
+
d && (d.fftSize = 128, R = new Uint8Array(d.frequencyBinCount));
|
|
18
|
+
const pe = () => {
|
|
19
|
+
I = requestAnimationFrame(pe), (p.width !== p.offsetWidth || p.height !== p.offsetHeight) && (p.width = p.offsetWidth, p.height = p.offsetHeight);
|
|
20
|
+
const oe = p.width, y = p.height;
|
|
21
|
+
if (oe === 0 || y === 0) return;
|
|
22
|
+
const _ = y / 2;
|
|
23
|
+
U.clearRect(0, 0, oe, y), U.fillStyle = "#1e293b";
|
|
24
|
+
const ee = 2, M = ee + 2, ue = oe * 0.95, g = Math.floor(ue / M);
|
|
25
|
+
(!v.current || v.current.length !== g) && (v.current = new Float32Array(g).fill(2));
|
|
26
|
+
const xe = g * M, te = (oe - xe) / 2;
|
|
27
|
+
d && R && d.getByteFrequencyData(R);
|
|
28
|
+
const me = R ? R.length : 0, q = Math.floor(me * 0.7) / g, F = new Float32Array(g);
|
|
29
29
|
for (let m = 0; m < g; m++) {
|
|
30
30
|
let $ = 0;
|
|
31
|
-
if (
|
|
32
|
-
const b = Math.floor(m *
|
|
33
|
-
for (let
|
|
34
|
-
const
|
|
35
|
-
|
|
31
|
+
if (R && q > 0) {
|
|
32
|
+
const b = Math.floor(m * q), Q = Math.floor((m + 1) * q);
|
|
33
|
+
for (let G = b; G < Q; G++) {
|
|
34
|
+
const de = R[G] || 0;
|
|
35
|
+
de > $ && ($ = de);
|
|
36
36
|
}
|
|
37
37
|
}
|
|
38
38
|
$ < 10 && ($ = 0);
|
|
39
|
-
const
|
|
40
|
-
|
|
39
|
+
const L = $ / 255, S = $ > 0 ? Math.max(2, Math.pow(L, 1.4) * y * 0.25) : 2;
|
|
40
|
+
F[m] = S;
|
|
41
41
|
}
|
|
42
42
|
for (let m = 0; m < g; m++) {
|
|
43
|
-
const $ = g - 1 - m,
|
|
44
|
-
|
|
45
|
-
const b =
|
|
46
|
-
|
|
43
|
+
const $ = g - 1 - m, L = Math.max(F[m], F[$]), S = v.current[m] + (L - v.current[m]) * 0.3;
|
|
44
|
+
v.current[m] = S;
|
|
45
|
+
const b = te + m * M, Q = _ - S / 2;
|
|
46
|
+
U.beginPath(), U.roundRect ? U.roundRect(b, Q, ee, S, 4) : U.fillRect(b, Q, ee, S), U.fill();
|
|
47
47
|
}
|
|
48
48
|
};
|
|
49
|
-
return
|
|
50
|
-
cancelAnimationFrame(
|
|
49
|
+
return pe(), () => {
|
|
50
|
+
cancelAnimationFrame(I);
|
|
51
51
|
};
|
|
52
|
-
}, [
|
|
52
|
+
}, [d]), /* @__PURE__ */ c(
|
|
53
53
|
"canvas",
|
|
54
54
|
{
|
|
55
|
-
ref:
|
|
55
|
+
ref: A,
|
|
56
56
|
style: { width: "100%", height: "100%", display: "block" }
|
|
57
57
|
}
|
|
58
58
|
);
|
|
59
|
-
},
|
|
60
|
-
async function
|
|
61
|
-
const
|
|
59
|
+
}, ht = "https://ai.streamoji.com", Vt = "https://pub-48df6f7d60d6440bbd01676ea5d90e55.r2.dev", pt = "https://pub-be53cae7bd99457a8c1f11b4d38f1672.r2.dev/default-models/fullbodyavatarmale.glb";
|
|
60
|
+
async function Ht(d) {
|
|
61
|
+
const A = await crypto.subtle.digest(
|
|
62
62
|
"SHA-256",
|
|
63
|
-
new TextEncoder().encode(
|
|
63
|
+
new TextEncoder().encode(d)
|
|
64
64
|
);
|
|
65
|
-
return Array.from(new Uint8Array(
|
|
65
|
+
return Array.from(new Uint8Array(A)).map((v) => v.toString(16).padStart(2, "0")).join("");
|
|
66
66
|
}
|
|
67
|
-
function
|
|
68
|
-
const [
|
|
69
|
-
return
|
|
70
|
-
if (!
|
|
71
|
-
|
|
67
|
+
function $t(d) {
|
|
68
|
+
const [A, v] = k(null);
|
|
69
|
+
return H(() => {
|
|
70
|
+
if (!d) {
|
|
71
|
+
v(null);
|
|
72
72
|
return;
|
|
73
73
|
}
|
|
74
74
|
let p = !1;
|
|
75
|
-
return
|
|
75
|
+
return Ht(d).then((U) => {
|
|
76
76
|
if (p) return;
|
|
77
|
-
const
|
|
78
|
-
fetch(
|
|
79
|
-
p ||
|
|
77
|
+
const I = `${Vt}/${U}.glb`;
|
|
78
|
+
fetch(I, { method: "HEAD" }).then((R) => {
|
|
79
|
+
p || v(R.ok ? I : pt);
|
|
80
80
|
}).catch(() => {
|
|
81
|
-
p ||
|
|
81
|
+
p || v(pt);
|
|
82
82
|
});
|
|
83
83
|
}), () => {
|
|
84
84
|
p = !0;
|
|
85
85
|
};
|
|
86
|
-
}, [
|
|
86
|
+
}, [d]), A;
|
|
87
87
|
}
|
|
88
|
-
const
|
|
88
|
+
const jt = [
|
|
89
89
|
"https://pub-be53cae7bd99457a8c1f11b4d38f1672.r2.dev/masculine/idle/M_Standing_Idle_Variations_001.glb",
|
|
90
90
|
"https://pub-be53cae7bd99457a8c1f11b4d38f1672.r2.dev/masculine/idle/M_Standing_Idle_Variations_002.glb",
|
|
91
91
|
"https://pub-be53cae7bd99457a8c1f11b4d38f1672.r2.dev/masculine/idle/M_Standing_Idle_002.glb",
|
|
92
92
|
"https://pub-be53cae7bd99457a8c1f11b4d38f1672.r2.dev/masculine/idle/M_Standing_Idle_Variations_005.glb"
|
|
93
|
-
],
|
|
93
|
+
], Jt = [
|
|
94
94
|
{
|
|
95
95
|
id: "m_expr_01",
|
|
96
96
|
name: "Friendly Wave",
|
|
@@ -256,17 +256,17 @@ const Bt = [
|
|
|
256
256
|
name: "Take It Easy",
|
|
257
257
|
url: "https://pub-be53cae7bd99457a8c1f11b4d38f1672.r2.dev/masculine/expression/F_Talking_Variations_006.glb"
|
|
258
258
|
}
|
|
259
|
-
],
|
|
259
|
+
], qt = [
|
|
260
260
|
"https://pub-be53cae7bd99457a8c1f11b4d38f1672.r2.dev/masculine/expression/M_Talking_Variations_005.glb",
|
|
261
261
|
"https://pub-be53cae7bd99457a8c1f11b4d38f1672.r2.dev/masculine/expression/M_Talking_Variations_007.glb"
|
|
262
|
-
],
|
|
262
|
+
], Gt = {
|
|
263
263
|
zoom: 0.85,
|
|
264
264
|
position: [0.15, -0.8, 0],
|
|
265
265
|
scale: 1.5,
|
|
266
266
|
rotation: [0.15, 0.02, 0]
|
|
267
|
-
},
|
|
267
|
+
}, zt = [-0.45, 1.9, 0.1], Yt = {
|
|
268
268
|
browInnerUp: 0.2
|
|
269
|
-
},
|
|
269
|
+
}, et = 0.18, Xt = 1, je = {
|
|
270
270
|
neutral: { eyeLookDownLeft: 0.1, eyeLookDownRight: 0.1 },
|
|
271
271
|
happy: {
|
|
272
272
|
mouthSmileLeft: 0.2,
|
|
@@ -348,7 +348,7 @@ const Bt = [
|
|
|
348
348
|
mouthUpperUpLeft: 0.1,
|
|
349
349
|
mouthUpperUpRight: 0.1
|
|
350
350
|
}
|
|
351
|
-
},
|
|
351
|
+
}, Kt = [
|
|
352
352
|
{ key: "viseme_aa", mix: { jawOpen: 0.6 } },
|
|
353
353
|
{
|
|
354
354
|
key: "viseme_E",
|
|
@@ -444,7 +444,7 @@ const Bt = [
|
|
|
444
444
|
}
|
|
445
445
|
},
|
|
446
446
|
{ key: "viseme_sil", mix: {} }
|
|
447
|
-
],
|
|
447
|
+
], Qt = {
|
|
448
448
|
aei: [
|
|
449
449
|
{ v: "E", w: 0.8 },
|
|
450
450
|
{ v: "I", w: 0.2 }
|
|
@@ -473,303 +473,317 @@ const Bt = [
|
|
|
473
473
|
],
|
|
474
474
|
sil: [{ v: "sil", w: 1 }]
|
|
475
475
|
};
|
|
476
|
-
function
|
|
477
|
-
if (!
|
|
478
|
-
const
|
|
479
|
-
return
|
|
476
|
+
function Zt(d) {
|
|
477
|
+
if (!d) return [{ v: "sil", w: 1 }];
|
|
478
|
+
const A = d.toLowerCase();
|
|
479
|
+
return Qt[A] ?? [{ v: "sil", w: 1 }];
|
|
480
480
|
}
|
|
481
|
-
function
|
|
482
|
-
const { camera:
|
|
483
|
-
return
|
|
484
|
-
|
|
485
|
-
}, [
|
|
481
|
+
function en({ target: d }) {
|
|
482
|
+
const { camera: A } = Ft();
|
|
483
|
+
return H(() => {
|
|
484
|
+
A.lookAt(...d);
|
|
485
|
+
}, [A, d]), null;
|
|
486
486
|
}
|
|
487
|
-
function
|
|
488
|
-
if (!
|
|
487
|
+
function Y(d, A, v) {
|
|
488
|
+
if (!d || !d.morphTargetDictionary)
|
|
489
489
|
return;
|
|
490
|
-
const p =
|
|
491
|
-
if (
|
|
492
|
-
for (const
|
|
493
|
-
|
|
490
|
+
const p = d, U = p.morphTargetDictionary, I = p.morphTargetInfluences;
|
|
491
|
+
if (I)
|
|
492
|
+
for (const R in U)
|
|
493
|
+
R.toLowerCase() === A.toLowerCase() && (I[U[R]] = v);
|
|
494
494
|
}
|
|
495
|
-
function
|
|
496
|
-
if (!
|
|
497
|
-
const
|
|
498
|
-
if (
|
|
499
|
-
for (let p = 0; p <
|
|
500
|
-
|
|
495
|
+
function mt(d, A = 0.97) {
|
|
496
|
+
if (!d) return;
|
|
497
|
+
const v = d;
|
|
498
|
+
if (v.morphTargetInfluences)
|
|
499
|
+
for (let p = 0; p < v.morphTargetInfluences.length; p++)
|
|
500
|
+
v.morphTargetInfluences[p] *= A;
|
|
501
501
|
}
|
|
502
|
-
const
|
|
502
|
+
const tn = Ut(
|
|
503
503
|
({
|
|
504
|
-
avatarUrl:
|
|
505
|
-
isPlayingRef:
|
|
506
|
-
visemeQueueRef:
|
|
504
|
+
avatarUrl: d,
|
|
505
|
+
isPlayingRef: A,
|
|
506
|
+
visemeQueueRef: v,
|
|
507
507
|
audioContextRef: p,
|
|
508
|
-
responseAudioStartTimeRef:
|
|
509
|
-
adjustments:
|
|
510
|
-
mood:
|
|
511
|
-
expression:
|
|
512
|
-
agentResponse:
|
|
513
|
-
isSpeaking:
|
|
514
|
-
nextStartTimeRef:
|
|
515
|
-
stopPlayback:
|
|
516
|
-
setIsSpeaking:
|
|
517
|
-
expressionUrl:
|
|
518
|
-
onExpressionFinished:
|
|
508
|
+
responseAudioStartTimeRef: U,
|
|
509
|
+
adjustments: I,
|
|
510
|
+
mood: R,
|
|
511
|
+
expression: pe,
|
|
512
|
+
agentResponse: oe,
|
|
513
|
+
isSpeaking: y,
|
|
514
|
+
nextStartTimeRef: _,
|
|
515
|
+
stopPlayback: ee,
|
|
516
|
+
setIsSpeaking: O,
|
|
517
|
+
expressionUrl: M,
|
|
518
|
+
onExpressionFinished: ue
|
|
519
519
|
}) => {
|
|
520
|
-
const { scene: g } =
|
|
521
|
-
() =>
|
|
522
|
-
[
|
|
523
|
-
),
|
|
524
|
-
() =>
|
|
525
|
-
[
|
|
526
|
-
),
|
|
527
|
-
|
|
528
|
-
if (!(!
|
|
529
|
-
if (
|
|
530
|
-
const s = `idle_${
|
|
531
|
-
if (!
|
|
532
|
-
const n =
|
|
533
|
-
n.name = s, n.setLoop(Fe.LoopOnce, 1), n.clampWhenFinished = !0,
|
|
520
|
+
const { scene: g } = Ze(d), xe = Ze(jt), te = tt(
|
|
521
|
+
() => xe.flatMap((f) => f.animations),
|
|
522
|
+
[xe]
|
|
523
|
+
), me = Ze(qt), ae = tt(
|
|
524
|
+
() => me.flatMap((f) => f.animations),
|
|
525
|
+
[me]
|
|
526
|
+
), q = o(null), F = o(null), m = o(null), $ = o([]), [L] = k(() => new Fe.AnimationMixer(g)), S = o({}), b = o(null), Q = o(0), G = o(!1), de = o(0), ne = o(null);
|
|
527
|
+
H(() => {
|
|
528
|
+
if (!(!te || !g)) {
|
|
529
|
+
if (te.forEach((f, u) => {
|
|
530
|
+
const s = `idle_${u}`;
|
|
531
|
+
if (!S.current[s]) {
|
|
532
|
+
const n = L.clipAction(f, g);
|
|
533
|
+
n.name = s, n.setLoop(Fe.LoopOnce, 1), n.clampWhenFinished = !0, S.current[s] = n;
|
|
534
534
|
}
|
|
535
|
-
}),
|
|
536
|
-
const s = `talk_${
|
|
537
|
-
if (!
|
|
538
|
-
const n =
|
|
539
|
-
n.name = s, n.setLoop(Fe.LoopOnce, 1), n.clampWhenFinished = !0,
|
|
535
|
+
}), ae.forEach((f, u) => {
|
|
536
|
+
const s = `talk_${u}`;
|
|
537
|
+
if (!S.current[s]) {
|
|
538
|
+
const n = L.clipAction(f, g);
|
|
539
|
+
n.name = s, n.setLoop(Fe.LoopOnce, 1), n.clampWhenFinished = !0, S.current[s] = n;
|
|
540
540
|
}
|
|
541
|
-
}),
|
|
542
|
-
const
|
|
543
|
-
|
|
541
|
+
}), te.length > 0) {
|
|
542
|
+
const f = S.current.idle_0, u = b.current && L.existingAction(b.current.getClip());
|
|
543
|
+
f && !u && (f.reset().fadeIn(0.5).play(), b.current = f);
|
|
544
544
|
}
|
|
545
545
|
return () => {
|
|
546
|
-
|
|
546
|
+
L.stopAllAction(), S.current = {}, b.current = null;
|
|
547
547
|
};
|
|
548
548
|
}
|
|
549
|
-
}, [
|
|
550
|
-
const
|
|
551
|
-
|
|
552
|
-
if (!
|
|
553
|
-
|
|
554
|
-
|
|
555
|
-
(
|
|
556
|
-
if (
|
|
557
|
-
const s =
|
|
558
|
-
if (n.name = `EXPR_${
|
|
549
|
+
}, [te, ae, g, L]);
|
|
550
|
+
const ke = o("");
|
|
551
|
+
H(() => {
|
|
552
|
+
if (!M || !g || M === ke.current) return;
|
|
553
|
+
ke.current = M, ne.current = M, new Bt().load(
|
|
554
|
+
M,
|
|
555
|
+
(u) => {
|
|
556
|
+
if (u.animations && u.animations.length > 0) {
|
|
557
|
+
const s = u.animations[0], n = L.clipAction(s, g);
|
|
558
|
+
if (n.name = `EXPR_${M}`, n.setLoop(Fe.LoopOnce, 1), n.clampWhenFinished = !0, S.current[`EXPR_${M}`] = n, y && ne.current === M) {
|
|
559
559
|
const h = b.current;
|
|
560
|
-
n.reset().fadeIn(0.3).play(), h && h !== n && h.crossFadeTo(n, 0.3, !0), b.current = n,
|
|
560
|
+
n.reset().fadeIn(0.3).play(), h && h !== n && h.crossFadeTo(n, 0.3, !0), b.current = n, ne.current = null;
|
|
561
561
|
}
|
|
562
562
|
}
|
|
563
563
|
},
|
|
564
564
|
void 0,
|
|
565
|
-
(
|
|
566
|
-
console.error(`[ANIMATION] Failed to load ${
|
|
565
|
+
(u) => {
|
|
566
|
+
console.error(`[ANIMATION] Failed to load ${M}`, u);
|
|
567
567
|
}
|
|
568
568
|
);
|
|
569
|
-
}, [
|
|
570
|
-
const
|
|
571
|
-
const s =
|
|
569
|
+
}, [M, g, L, y]), H(() => {
|
|
570
|
+
const f = (u) => {
|
|
571
|
+
const s = u.action, n = s.name || "";
|
|
572
572
|
if (n.startsWith("idle_")) {
|
|
573
|
-
const
|
|
574
|
-
|
|
573
|
+
const j = (parseInt(n.split("_")[1]) + 1) % te.length, X = S.current[`idle_${j}`];
|
|
574
|
+
X && (X.reset().fadeIn(0.5).play(), s.crossFadeTo(X, 0.5, !0), b.current = X);
|
|
575
575
|
} else if (n.startsWith("EXPR_")) {
|
|
576
|
-
if (
|
|
577
|
-
const h =
|
|
576
|
+
if (y) {
|
|
577
|
+
const h = S.current.talk_0;
|
|
578
578
|
h && (h.reset().fadeIn(0.5).play(), s.crossFadeTo(h, 0.5, !0), b.current = h);
|
|
579
579
|
} else {
|
|
580
|
-
const h =
|
|
580
|
+
const h = S.current.idle_0;
|
|
581
581
|
h && (h.reset().fadeIn(0.5).play(), s.crossFadeTo(h, 0.5, !0), b.current = h);
|
|
582
582
|
}
|
|
583
|
-
|
|
583
|
+
ue && ue();
|
|
584
584
|
} else if (n.startsWith("talk_"))
|
|
585
|
-
if (
|
|
586
|
-
const
|
|
587
|
-
|
|
585
|
+
if (y) {
|
|
586
|
+
const j = (parseInt(n.split("_")[1]) + 1) % ae.length, X = S.current[`talk_${j}`];
|
|
587
|
+
X && (X.reset().fadeIn(0.3).play(), s.crossFadeTo(X, 0.3, !0), b.current = X);
|
|
588
588
|
} else {
|
|
589
|
-
const h =
|
|
589
|
+
const h = S.current.idle_0;
|
|
590
590
|
h && (h.reset().fadeIn(0.5).play(), s.crossFadeTo(h, 0.5, !0), b.current = h);
|
|
591
591
|
}
|
|
592
592
|
};
|
|
593
|
-
return
|
|
593
|
+
return L.addEventListener("finished", f), () => L.removeEventListener("finished", f);
|
|
594
594
|
}, [
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
|
|
600
|
-
]),
|
|
601
|
-
if (
|
|
602
|
-
const
|
|
603
|
-
if (
|
|
604
|
-
const s =
|
|
595
|
+
L,
|
|
596
|
+
te,
|
|
597
|
+
ae,
|
|
598
|
+
y,
|
|
599
|
+
ue
|
|
600
|
+
]), H(() => {
|
|
601
|
+
if (y && g) {
|
|
602
|
+
const f = b.current, u = f?.name || "";
|
|
603
|
+
if (u.startsWith("idle_") || u.startsWith("talk_") || u === "") {
|
|
604
|
+
const s = ne.current;
|
|
605
605
|
if (s) {
|
|
606
|
-
const n =
|
|
606
|
+
const n = S.current[`EXPR_${s}`];
|
|
607
607
|
if (n) {
|
|
608
|
-
n.reset().fadeIn(0.3).play(),
|
|
608
|
+
n.reset().fadeIn(0.3).play(), f && f !== n && f.crossFadeTo(n, 0.3, !0), b.current = n, ne.current = null;
|
|
609
609
|
return;
|
|
610
610
|
}
|
|
611
611
|
}
|
|
612
|
-
if (
|
|
613
|
-
const n =
|
|
614
|
-
n && (n.reset().fadeIn(0.5).play(),
|
|
612
|
+
if (u.startsWith("idle_") || u === "") {
|
|
613
|
+
const n = S.current.talk_0;
|
|
614
|
+
n && (n.reset().fadeIn(0.5).play(), f && f.crossFadeTo(n, 0.5, !0), b.current = n);
|
|
615
615
|
}
|
|
616
616
|
}
|
|
617
|
-
} else if (!
|
|
618
|
-
const
|
|
619
|
-
if (
|
|
620
|
-
const s =
|
|
621
|
-
s && (s.reset().fadeIn(0.5).play(),
|
|
617
|
+
} else if (!y && g) {
|
|
618
|
+
const f = b.current, u = f?.name || "";
|
|
619
|
+
if (u.startsWith("talk_") || u.startsWith("EXPR_")) {
|
|
620
|
+
const s = S.current.idle_0;
|
|
621
|
+
s && (s.reset().fadeIn(0.5).play(), f && f.crossFadeTo(s, 0.5, !0), b.current = s);
|
|
622
622
|
}
|
|
623
623
|
}
|
|
624
|
-
}, [
|
|
624
|
+
}, [y, g, M]), H(() => {
|
|
625
625
|
if (!g) return;
|
|
626
626
|
g.traverse((s) => {
|
|
627
627
|
if (s.isMesh && s.morphTargetDictionary) {
|
|
628
628
|
const n = s.name.toLowerCase();
|
|
629
|
-
(n.includes("head") || n.includes("avatar")) && (
|
|
629
|
+
(n.includes("head") || n.includes("avatar")) && (F.current = s, W(`[ANIMATION] Found head mesh: ${s.name}`)), n.includes("teeth") && (m.current = s, W(`[ANIMATION] Found teeth mesh: ${s.name}`));
|
|
630
630
|
}
|
|
631
631
|
});
|
|
632
|
-
const
|
|
633
|
-
|
|
632
|
+
const f = F.current?.morphTargetDictionary;
|
|
633
|
+
f && Object.keys(f).filter(
|
|
634
634
|
(s) => s.toLowerCase().includes("brow")
|
|
635
635
|
);
|
|
636
|
-
const
|
|
636
|
+
const u = [];
|
|
637
637
|
g.traverse((s) => {
|
|
638
638
|
if (s.isMesh) {
|
|
639
639
|
const h = s.morphTargetDictionary;
|
|
640
|
-
h && Object.keys(h).some((
|
|
640
|
+
h && Object.keys(h).some((j) => j.toLowerCase().includes("brow")) && u.push(s);
|
|
641
641
|
}
|
|
642
|
-
}), $.current =
|
|
642
|
+
}), $.current = u, u.length > 0 && W("[ANIMATION] Meshes with brow morphs:", u.length);
|
|
643
643
|
}, [g]);
|
|
644
|
-
const Ue = (
|
|
645
|
-
const s = `viseme_${
|
|
644
|
+
const Ue = (f, u = 1) => {
|
|
645
|
+
const s = `viseme_${f}`.toLowerCase(), n = Kt.find((h) => h.key.toLowerCase() === s);
|
|
646
646
|
if (n)
|
|
647
647
|
for (const h in n.mix) {
|
|
648
|
-
const
|
|
649
|
-
|
|
648
|
+
const j = n.mix[h] * u;
|
|
649
|
+
Y(F.current, h, j), Y(m.current, h, j);
|
|
650
650
|
}
|
|
651
|
-
},
|
|
652
|
-
const
|
|
653
|
-
for (const s in
|
|
654
|
-
|
|
651
|
+
}, Ie = (f) => {
|
|
652
|
+
const u = je[f] ?? je.neutral;
|
|
653
|
+
for (const s in u)
|
|
654
|
+
Y(F.current, s, u[s]), Y(m.current, s, u[s]);
|
|
655
655
|
};
|
|
656
|
-
return
|
|
657
|
-
const s = Math.pow(0.88, 60 *
|
|
658
|
-
|
|
659
|
-
const n =
|
|
656
|
+
return Dt((f, u) => {
|
|
657
|
+
const s = Math.pow(0.88, 60 * u);
|
|
658
|
+
mt(F.current, s), mt(m.current, s), Ie(R);
|
|
659
|
+
const n = f.clock.elapsedTime;
|
|
660
660
|
let h = 0;
|
|
661
|
-
if (Math.floor(n) % 5 === 0 && Math.floor((n -
|
|
662
|
-
let
|
|
663
|
-
g.traverse((
|
|
664
|
-
|
|
661
|
+
if (Math.floor(n) % 5 === 0 && Math.floor((n - u) % 5) !== 0) {
|
|
662
|
+
let J = null;
|
|
663
|
+
g.traverse((z) => {
|
|
664
|
+
z.name.toLowerCase().includes("hips") && (J = z);
|
|
665
665
|
});
|
|
666
|
-
const
|
|
667
|
-
|
|
666
|
+
const P = J ? `Hips Y: ${J.position.y.toFixed(4)}` : "Hips not found";
|
|
667
|
+
W(`[ANIMATION] Mixer Time: ${L.time.toFixed(2)}, ${P}`);
|
|
668
668
|
}
|
|
669
|
-
if (
|
|
670
|
-
const
|
|
671
|
-
if (
|
|
672
|
-
|
|
669
|
+
if (L.update(u), n > Q.current && !G.current && (G.current = !0, de.current = n), G.current) {
|
|
670
|
+
const P = (n - de.current) / 0.3;
|
|
671
|
+
if (P >= 1)
|
|
672
|
+
G.current = !1, Q.current = n + 2 + Math.random() * 5;
|
|
673
673
|
else {
|
|
674
|
-
const
|
|
675
|
-
|
|
674
|
+
const z = P < 0.5 ? P * 2 : (1 - P) * 2;
|
|
675
|
+
Y(F.current, "eyeBlinkLeft", z), Y(F.current, "eyeBlinkRight", z), Y(m.current, "eyeBlinkLeft", z), Y(m.current, "eyeBlinkRight", z), h = z * Yt.browInnerUp;
|
|
676
676
|
}
|
|
677
677
|
}
|
|
678
|
-
const
|
|
679
|
-
if (
|
|
680
|
-
const
|
|
681
|
-
|
|
682
|
-
|
|
683
|
-
|
|
678
|
+
const j = je[R] ?? je.neutral, X = j.browInnerUp ?? 0, _e = j.browOuterUpLeft ?? 0, ge = j.browOuterUpRight ?? 0, Re = n * Xt, be = et * Math.sin(Re), we = et * 0.7 * Math.sin(Re + 0.7), Ce = et * 0.7 * Math.sin(Re + 1.3), ve = (J) => Math.max(0, Math.min(1, J)), De = ve(X + be), Ae = ve(_e + we), Je = ve(ge + Ce), Ne = ve(De + h);
|
|
679
|
+
if (Y(F.current, "browInnerUp", Ne), Y(m.current, "browInnerUp", Ne), Y(F.current, "browOuterUpLeft", Ae), Y(m.current, "browOuterUpLeft", Ae), Y(F.current, "browOuterUpRight", Je), Y(m.current, "browOuterUpRight", Je), q.current) {
|
|
680
|
+
const J = A.current ? 0 : I.rotation[1];
|
|
681
|
+
q.current.rotation.y = Fe.MathUtils.lerp(
|
|
682
|
+
q.current.rotation.y,
|
|
683
|
+
J,
|
|
684
684
|
0.1
|
|
685
|
-
),
|
|
685
|
+
), q.current.position.set(...I.position), q.current.scale.setScalar(I.scale), q.current.rotation.x = I.rotation[0], q.current.rotation.z = I.rotation[2];
|
|
686
686
|
}
|
|
687
|
-
if (
|
|
688
|
-
const
|
|
689
|
-
for (let
|
|
690
|
-
const
|
|
691
|
-
|
|
687
|
+
if (A.current && p.current) {
|
|
688
|
+
const J = p.current.currentTime, Oe = (J - U.current) * 1e3 - -150;
|
|
689
|
+
for (let Le = 0; Le < v.current.length; Le++) {
|
|
690
|
+
const Z = v.current[Le];
|
|
691
|
+
Oe >= Z.vtime && Oe < Z.vtime + Z.vduration && Ue(Z.viseme, Z.weight ?? 1);
|
|
692
692
|
}
|
|
693
|
-
|
|
693
|
+
J > _.current + 0.5 && (ee(), O(!1));
|
|
694
694
|
}
|
|
695
|
-
}), /* @__PURE__ */
|
|
695
|
+
}), /* @__PURE__ */ c("group", { ref: q, children: /* @__PURE__ */ c("primitive", { object: g }) });
|
|
696
696
|
}
|
|
697
697
|
);
|
|
698
|
-
function
|
|
699
|
-
return
|
|
698
|
+
function nn(d) {
|
|
699
|
+
return d ? d.charAt(0).toUpperCase() + d.slice(1).toLowerCase() : "";
|
|
700
700
|
}
|
|
701
|
-
const
|
|
702
|
-
token:
|
|
703
|
-
agentToken:
|
|
704
|
-
onNavigationRequested:
|
|
701
|
+
const rn = ({
|
|
702
|
+
token: d,
|
|
703
|
+
agentToken: A,
|
|
704
|
+
onNavigationRequested: v
|
|
705
705
|
} = {}) => {
|
|
706
|
-
const p =
|
|
706
|
+
const p = d ?? A ?? "", U = $t(p || void 0), [I, R] = k(""), [pe, oe] = k(""), [y, _] = k("Ready"), [ee, O] = k(!1), [M, ue] = k(!1), [g, xe] = k(
|
|
707
707
|
() => typeof window < "u" ? window.matchMedia("(max-width: 480px)").matches : !1
|
|
708
708
|
);
|
|
709
|
-
|
|
710
|
-
const e = window.matchMedia("(max-width: 480px)"), t = () =>
|
|
709
|
+
H(() => {
|
|
710
|
+
const e = window.matchMedia("(max-width: 480px)"), t = () => xe(e.matches);
|
|
711
711
|
return e.addEventListener("change", t), () => e.removeEventListener("change", t);
|
|
712
712
|
}, []);
|
|
713
|
-
const
|
|
713
|
+
const te = g ? 80 : 600, me = o(!1), ae = o([]), q = o(0), F = o(!1), m = o([]), $ = o(null), L = o([]);
|
|
714
714
|
o([]);
|
|
715
|
-
const
|
|
715
|
+
const S = o([]), b = o(0), Q = o(0), G = o(0), de = o(0), ne = o(!1), [ke, Ue] = k(
|
|
716
716
|
null
|
|
717
|
-
),
|
|
717
|
+
), Ie = o(null), [f, u] = k("neutral"), [s, n] = k(""), [h, j] = k(""), [X, _e] = k("Chat with us"), [ge, Re] = k(
|
|
718
718
|
null
|
|
719
|
-
), [
|
|
720
|
-
|
|
721
|
-
const [
|
|
722
|
-
|
|
723
|
-
const
|
|
724
|
-
|
|
725
|
-
const e =
|
|
719
|
+
), [be, we] = k("hidden"), [Ce, ve] = k(""), De = o(null), Ae = o(be);
|
|
720
|
+
Ae.current = be;
|
|
721
|
+
const [Je, Ne] = k(null), J = o(null), P = o(null), [z, Oe] = k(!1), Le = o(null), [Z, We] = k("hidden"), [nt, gt] = k(""), qe = o(Z);
|
|
722
|
+
qe.current = Z;
|
|
723
|
+
const fe = o(""), Te = o(!1), Me = o(""), Ee = tt(() => z ? "Try again" : y === "Busy" ? "Busy" : y === "Thinking..." || y === "Processing Voice..." ? y : ge != null && ge !== "" && ge !== "none" && ge !== "<none>" ? `Enter ${nn(ge)}` : null, [y, ge, z]), Be = Ee != null && Ee !== "";
|
|
724
|
+
H(() => {
|
|
725
|
+
const e = Ae.current;
|
|
726
726
|
if (!(e === "exiting" || e === "entering")) {
|
|
727
727
|
if (e === "hidden") {
|
|
728
|
-
|
|
728
|
+
Be && (ve(Ee ?? ""), we("entering"));
|
|
729
729
|
return;
|
|
730
730
|
}
|
|
731
|
-
e === "visible" && (!
|
|
731
|
+
e === "visible" && (!Be || Ee !== Ce) && (De.current = Be ? Ee : null, we("exiting"));
|
|
732
732
|
}
|
|
733
733
|
}, [
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
|
|
737
|
-
|
|
738
|
-
])
|
|
739
|
-
|
|
740
|
-
|
|
734
|
+
Be,
|
|
735
|
+
Ee,
|
|
736
|
+
be,
|
|
737
|
+
Ce
|
|
738
|
+
]), H(() => {
|
|
739
|
+
if (y !== "Busy") {
|
|
740
|
+
P.current != null && (clearTimeout(P.current), P.current = null);
|
|
741
|
+
return;
|
|
742
|
+
}
|
|
743
|
+
return P.current = setTimeout(() => {
|
|
744
|
+
P.current = null, _("Ready"), Oe(!0);
|
|
745
|
+
}, 12e3), () => {
|
|
746
|
+
P.current != null && (clearTimeout(P.current), P.current = null);
|
|
747
|
+
};
|
|
748
|
+
}, [y]), H(() => {
|
|
749
|
+
if (!z) return;
|
|
750
|
+
const e = setTimeout(() => Oe(!1), 2500);
|
|
751
|
+
return () => clearTimeout(e);
|
|
752
|
+
}, [z]);
|
|
753
|
+
const bt = $e(() => {
|
|
754
|
+
const e = Ae.current;
|
|
741
755
|
if (e === "exiting") {
|
|
742
|
-
|
|
743
|
-
const t =
|
|
744
|
-
|
|
745
|
-
} else e === "entering" &&
|
|
746
|
-
}, []),
|
|
756
|
+
we("hidden");
|
|
757
|
+
const t = De.current;
|
|
758
|
+
De.current = null, t != null && t !== "" && (ve(t), we("entering"));
|
|
759
|
+
} else e === "entering" && we("visible");
|
|
760
|
+
}, []), _t = (e) => {
|
|
747
761
|
if (!e) return;
|
|
748
762
|
if (e.mood != null) {
|
|
749
763
|
const r = String(e.mood).toLowerCase();
|
|
750
|
-
|
|
764
|
+
u(r);
|
|
751
765
|
}
|
|
752
766
|
if (e.expression != null) {
|
|
753
767
|
const r = String(e.expression).trim();
|
|
754
768
|
n(r);
|
|
755
|
-
const
|
|
756
|
-
(
|
|
769
|
+
const a = Jt.find(
|
|
770
|
+
(w) => w.name.toLowerCase() === r.toLowerCase()
|
|
757
771
|
);
|
|
758
|
-
|
|
759
|
-
`[STREAM] Animation match for "${r}": ${
|
|
760
|
-
),
|
|
772
|
+
W(
|
|
773
|
+
`[STREAM] Animation match for "${r}": ${a ? a.name : "NONE"}`
|
|
774
|
+
), j(a?.url ?? "");
|
|
761
775
|
}
|
|
762
776
|
if (e.navigation != null) {
|
|
763
777
|
const r = String(e.navigation).trim();
|
|
764
|
-
r !== "" && (
|
|
778
|
+
r !== "" && (v ? v(r) : window.open(r, "_blank"));
|
|
765
779
|
}
|
|
766
|
-
const t = e.ask_for || e.lead_capture?.ask_for, i = t ? String(t).trim().toLowerCase() : "",
|
|
767
|
-
if (t && !
|
|
780
|
+
const t = e.ask_for || e.lead_capture?.ask_for, i = t ? String(t).trim().toLowerCase() : "", l = i === "none" || i === "<none>";
|
|
781
|
+
if (t && !l) {
|
|
768
782
|
const r = i;
|
|
769
|
-
|
|
770
|
-
} else (
|
|
783
|
+
Re(r || null), _e(r === "email" ? "Enter your email" : r === "name" ? "Enter your name" : r === "phone" ? "Enter your phone number" : "Chat with us");
|
|
784
|
+
} else (l || e.ask_for === null || e.lead_capture && e.lead_capture.ask_for === null || e.ask_for === "none") && (Re(null), X !== "Chat with us" && _e("Chat with us"));
|
|
771
785
|
e.collected, e.valid;
|
|
772
|
-
},
|
|
786
|
+
}, wt = (e) => {
|
|
773
787
|
const t = e.trim();
|
|
774
788
|
if (!t) return null;
|
|
775
789
|
if (t.startsWith("{"))
|
|
@@ -779,50 +793,50 @@ const en = ({
|
|
|
779
793
|
return null;
|
|
780
794
|
}
|
|
781
795
|
if (t.includes(":")) {
|
|
782
|
-
const i = t.split(":"),
|
|
783
|
-
return { [
|
|
796
|
+
const i = t.split(":"), l = i[0].trim().toLowerCase(), r = i.slice(1).join(":").trim();
|
|
797
|
+
return { [l]: r };
|
|
784
798
|
}
|
|
785
799
|
return null;
|
|
786
|
-
},
|
|
787
|
-
}, []),
|
|
788
|
-
if (
|
|
789
|
-
e === "§" ?
|
|
800
|
+
}, vt = $e(() => {
|
|
801
|
+
}, []), rt = (e) => {
|
|
802
|
+
if (Te.current)
|
|
803
|
+
e === "§" ? Te.current = !1 : (Me.current += e, oe((t) => t + e));
|
|
790
804
|
else if (e === "§") {
|
|
791
|
-
|
|
805
|
+
Te.current = !0;
|
|
792
806
|
return;
|
|
793
807
|
} else
|
|
794
|
-
for (
|
|
808
|
+
for (fe.current += e; fe.current.includes(`
|
|
795
809
|
`); ) {
|
|
796
|
-
const t =
|
|
797
|
-
`), i =
|
|
798
|
-
|
|
799
|
-
const
|
|
800
|
-
|
|
810
|
+
const t = fe.current.indexOf(`
|
|
811
|
+
`), i = fe.current.slice(0, t).trim();
|
|
812
|
+
fe.current = fe.current.slice(t + 1);
|
|
813
|
+
const l = wt(i);
|
|
814
|
+
l && _t(l);
|
|
801
815
|
}
|
|
802
816
|
};
|
|
803
|
-
|
|
817
|
+
H(() => {
|
|
804
818
|
(async () => {
|
|
805
819
|
if (!sessionStorage.getItem(
|
|
806
820
|
"STREAMOJI_LEADS_SESSION_LEAD_ID"
|
|
807
821
|
)) {
|
|
808
|
-
const i = "secret",
|
|
822
|
+
const i = "secret", l = Math.floor(Date.now() / 1e3).toString();
|
|
809
823
|
try {
|
|
810
|
-
const r = new TextEncoder(),
|
|
824
|
+
const r = new TextEncoder(), a = await crypto.subtle.importKey(
|
|
811
825
|
"raw",
|
|
812
826
|
r.encode(i),
|
|
813
827
|
{ name: "HMAC", hash: "SHA-256" },
|
|
814
828
|
!1,
|
|
815
829
|
["sign"]
|
|
816
|
-
),
|
|
830
|
+
), w = await crypto.subtle.sign(
|
|
817
831
|
"HMAC",
|
|
818
|
-
|
|
819
|
-
r.encode(
|
|
820
|
-
),
|
|
821
|
-
sessionStorage.setItem("STREAMOJI_LEADS_SESSION_LEAD_ID",
|
|
832
|
+
a,
|
|
833
|
+
r.encode(l)
|
|
834
|
+
), N = Array.from(new Uint8Array(w)).map((x) => x.toString(16).padStart(2, "0")).join("");
|
|
835
|
+
sessionStorage.setItem("STREAMOJI_LEADS_SESSION_LEAD_ID", N), W("[SESSION] New HMAC UID generated and saved:", N);
|
|
822
836
|
} catch (r) {
|
|
823
837
|
console.error("[SESSION] HMAC generation failed:", r);
|
|
824
|
-
const
|
|
825
|
-
sessionStorage.setItem("STREAMOJI_LEADS_SESSION_LEAD_ID",
|
|
838
|
+
const a = Math.random().toString(36) + Date.now().toString();
|
|
839
|
+
sessionStorage.setItem("STREAMOJI_LEADS_SESSION_LEAD_ID", a);
|
|
826
840
|
}
|
|
827
841
|
}
|
|
828
842
|
sessionStorage.getItem("STREAMOJI_LEADS_SESSION_MESSAGES") || sessionStorage.setItem(
|
|
@@ -831,7 +845,7 @@ const en = ({
|
|
|
831
845
|
);
|
|
832
846
|
})();
|
|
833
847
|
}, []);
|
|
834
|
-
const
|
|
848
|
+
const st = () => {
|
|
835
849
|
try {
|
|
836
850
|
return JSON.parse(
|
|
837
851
|
sessionStorage.getItem("STREAMOJI_LEADS_SESSION_MESSAGES") || "[]"
|
|
@@ -839,223 +853,232 @@ const en = ({
|
|
|
839
853
|
} catch {
|
|
840
854
|
return [];
|
|
841
855
|
}
|
|
842
|
-
},
|
|
856
|
+
}, yt = (e) => {
|
|
843
857
|
sessionStorage.setItem(
|
|
844
858
|
"STREAMOJI_LEADS_SESSION_MESSAGES",
|
|
845
859
|
JSON.stringify(e)
|
|
846
860
|
);
|
|
847
|
-
}, [
|
|
861
|
+
}, [Ge, ze] = k(!1), [it, Ye] = k(0), ce = o(null), Pe = o([]), ot = o(0), [at, St] = k(
|
|
848
862
|
null
|
|
849
|
-
), [
|
|
863
|
+
), [xt, Xe] = k(
|
|
850
864
|
null
|
|
851
|
-
),
|
|
865
|
+
), he = o(null), ye = o(
|
|
852
866
|
null
|
|
853
867
|
), Ve = $e((e = !1) => {
|
|
854
|
-
e && (
|
|
868
|
+
e && (ne.current = !0, O(!1), _("Ready")), m.current = [], ae.current = [], F.current = !1, ue(!1), b.current = 0, Q.current = 0, G.current = 0, L.current.forEach((t) => {
|
|
855
869
|
try {
|
|
856
870
|
t.stop();
|
|
857
871
|
} catch {
|
|
858
872
|
}
|
|
859
|
-
}),
|
|
860
|
-
}, []),
|
|
873
|
+
}), J.current && (clearTimeout(J.current), J.current = null), Ne(null), j(""), L.current = [];
|
|
874
|
+
}, []), kt = async () => {
|
|
861
875
|
try {
|
|
862
|
-
const e = await navigator.mediaDevices.getUserMedia({ audio: !0 }), t = window.AudioContext || window.webkitAudioContext, i = new t(),
|
|
863
|
-
r.fftSize = 64,
|
|
864
|
-
const
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
},
|
|
868
|
-
const
|
|
869
|
-
if (
|
|
870
|
-
|
|
876
|
+
const e = await navigator.mediaDevices.getUserMedia({ audio: !0 }), t = window.AudioContext || window.webkitAudioContext, i = new t(), l = i.createMediaStreamSource(e), r = i.createAnalyser();
|
|
877
|
+
r.fftSize = 64, l.connect(r), he.current = i, ye.current = l, Xe(r);
|
|
878
|
+
const a = new MediaRecorder(e);
|
|
879
|
+
ce.current = a, Pe.current = [], a.ondataavailable = (w) => {
|
|
880
|
+
w.data.size > 0 && Pe.current.push(w.data);
|
|
881
|
+
}, a.onstop = async () => {
|
|
882
|
+
const w = Date.now() - ot.current;
|
|
883
|
+
if (Xe(null), ye.current && (ye.current.disconnect(), ye.current = null), he.current && he.current.state !== "closed" && (he.current.close(), he.current = null), w < 1e3) {
|
|
884
|
+
_("Recording too short. Hold or click longer."), O(!1);
|
|
871
885
|
return;
|
|
872
886
|
}
|
|
873
|
-
const
|
|
887
|
+
const T = new Blob(Pe.current, {
|
|
874
888
|
type: "audio/wav"
|
|
875
889
|
});
|
|
876
|
-
await
|
|
877
|
-
},
|
|
890
|
+
await Tt(T);
|
|
891
|
+
}, ot.current = Date.now(), a.start(100), ze(!0), _("Listening...");
|
|
878
892
|
} catch (e) {
|
|
879
|
-
console.error("Error accessing microphone:", e),
|
|
893
|
+
console.error("Error accessing microphone:", e), _("Mic Access Error");
|
|
880
894
|
}
|
|
881
|
-
},
|
|
882
|
-
|
|
883
|
-
},
|
|
884
|
-
|
|
895
|
+
}, Rt = () => {
|
|
896
|
+
ce.current && ce.current.state !== "inactive" && (ce.current.stop(), ce.current.stream.getTracks().forEach((e) => e.stop()), ze(!1));
|
|
897
|
+
}, At = () => {
|
|
898
|
+
ce.current && ce.current.state !== "inactive" && (ce.current.onstop = null, ce.current.stop(), ce.current.stream.getTracks().forEach((e) => e.stop()), Xe(null), ye.current && (ye.current.disconnect(), ye.current = null), he.current && he.current.state !== "closed" && (he.current.close(), he.current = null), ze(!1), Pe.current = [], _("Ready"));
|
|
885
899
|
};
|
|
886
|
-
|
|
887
|
-
if (!
|
|
900
|
+
H(() => {
|
|
901
|
+
if (!M) return;
|
|
888
902
|
const e = () => {
|
|
889
|
-
const t =
|
|
903
|
+
const t = G.current;
|
|
890
904
|
if (t <= 0) return;
|
|
891
|
-
const i = $.current,
|
|
905
|
+
const i = $.current, l = b.current;
|
|
892
906
|
if (!i) return;
|
|
893
|
-
const r = i.currentTime -
|
|
894
|
-
if (
|
|
895
|
-
const
|
|
896
|
-
Math.round(
|
|
897
|
-
|
|
907
|
+
const r = i.currentTime - l, a = Math.min(Math.max(0, r), t), w = pe.trim().length;
|
|
908
|
+
if (w <= 0) return;
|
|
909
|
+
const T = Math.min(
|
|
910
|
+
Math.round(a / t * w),
|
|
911
|
+
w
|
|
898
912
|
);
|
|
899
|
-
Ue(
|
|
913
|
+
Ue(T);
|
|
900
914
|
};
|
|
901
|
-
return clearInterval(
|
|
902
|
-
}, [
|
|
915
|
+
return clearInterval(Ie.current ?? void 0), Ie.current = setInterval(e, 90), () => clearInterval(Ie.current ?? void 0);
|
|
916
|
+
}, [M, pe, G.current]), H(() => {
|
|
903
917
|
let e;
|
|
904
|
-
return
|
|
905
|
-
|
|
906
|
-
}, 1e3)) :
|
|
907
|
-
}, [
|
|
908
|
-
const
|
|
909
|
-
const t = e.numberOfChannels, i = e.length * t * 2 + 44,
|
|
910
|
-
let
|
|
911
|
-
const
|
|
912
|
-
r.setUint16(
|
|
913
|
-
},
|
|
914
|
-
r.setUint32(
|
|
918
|
+
return Ge ? (Ye(0), e = window.setInterval(() => {
|
|
919
|
+
Ye((t) => t + 1);
|
|
920
|
+
}, 1e3)) : Ye(0), () => clearInterval(e);
|
|
921
|
+
}, [Ge]);
|
|
922
|
+
const Lt = (e) => {
|
|
923
|
+
const t = e.numberOfChannels, i = e.length * t * 2 + 44, l = new ArrayBuffer(i), r = new DataView(l);
|
|
924
|
+
let a = 0;
|
|
925
|
+
const w = (C) => {
|
|
926
|
+
r.setUint16(a, C, !0), a += 2;
|
|
927
|
+
}, T = (C) => {
|
|
928
|
+
r.setUint32(a, C, !0), a += 4;
|
|
915
929
|
};
|
|
916
|
-
|
|
917
|
-
const
|
|
918
|
-
for (let
|
|
919
|
-
let
|
|
920
|
-
for (;
|
|
921
|
-
for (let
|
|
922
|
-
let
|
|
923
|
-
|
|
930
|
+
T(1179011410), T(i - 8), T(1163280727), T(544501094), T(16), w(1), w(t), T(e.sampleRate), T(e.sampleRate * 2 * t), w(t * 2), w(16), T(1635017060), T(i - a - 4);
|
|
931
|
+
const N = [];
|
|
932
|
+
for (let C = 0; C < t; C++) N.push(e.getChannelData(C));
|
|
933
|
+
let x = 0;
|
|
934
|
+
for (; a < i; ) {
|
|
935
|
+
for (let C = 0; C < t; C++) {
|
|
936
|
+
let B = Math.max(-1, Math.min(1, N[C][x]));
|
|
937
|
+
B = B < 0 ? B * 32768 : B * 32767, r.setInt16(a, B, !0), a += 2;
|
|
924
938
|
}
|
|
925
|
-
|
|
939
|
+
x++;
|
|
926
940
|
}
|
|
927
|
-
return new Blob([
|
|
928
|
-
},
|
|
929
|
-
if (!
|
|
930
|
-
if (
|
|
931
|
-
|
|
941
|
+
return new Blob([l], { type: "audio/wav" });
|
|
942
|
+
}, Ke = async (e, t, i = !1) => {
|
|
943
|
+
if (!ne.current) {
|
|
944
|
+
if (me.current) {
|
|
945
|
+
ae.current.push({
|
|
932
946
|
audio: e,
|
|
933
947
|
visemes: t,
|
|
934
948
|
isNewSegment: i
|
|
935
949
|
});
|
|
936
950
|
return;
|
|
937
951
|
}
|
|
938
|
-
|
|
952
|
+
me.current = !0;
|
|
939
953
|
try {
|
|
940
|
-
const
|
|
954
|
+
const l = window.AudioContext || window.webkitAudioContext, r = $.current ?? new l();
|
|
941
955
|
r.state === "suspended" && await r.resume(), $.current = r;
|
|
942
|
-
const
|
|
943
|
-
for (let
|
|
944
|
-
|
|
945
|
-
const
|
|
946
|
-
|
|
947
|
-
const
|
|
948
|
-
let
|
|
949
|
-
const
|
|
950
|
-
|
|
951
|
-
const
|
|
952
|
-
|
|
953
|
-
let V =
|
|
954
|
-
if ((!V || V.context !== r) && (V = r.createAnalyser(), V.fftSize = 64, V.connect(r.destination),
|
|
955
|
-
|
|
956
|
+
const a = window.atob(e), w = new Uint8Array(a.length);
|
|
957
|
+
for (let D = 0; D < a.length; D++)
|
|
958
|
+
w[D] = a.charCodeAt(D);
|
|
959
|
+
const T = await r.decodeAudioData(w.buffer.slice(0));
|
|
960
|
+
G.current += T.duration;
|
|
961
|
+
const N = r.currentTime;
|
|
962
|
+
let x = Q.current;
|
|
963
|
+
const C = !F.current;
|
|
964
|
+
x < N && (x = N + 0.1), Q.current = x + T.duration;
|
|
965
|
+
const B = r.createBufferSource();
|
|
966
|
+
B.buffer = T;
|
|
967
|
+
let V = at;
|
|
968
|
+
if ((!V || V.context !== r) && (V = r.createAnalyser(), V.fftSize = 64, V.connect(r.destination), St(V)), B.connect(V), L.current.push(B), ne.current) {
|
|
969
|
+
L.current = L.current.filter((D) => D !== B);
|
|
956
970
|
return;
|
|
957
971
|
}
|
|
958
|
-
if (
|
|
959
|
-
|
|
960
|
-
`[AUDIO] setIsSpeaking(true) - First chunk starting at ${
|
|
972
|
+
if (C) {
|
|
973
|
+
F.current = !0, ue(!0), W(
|
|
974
|
+
`[AUDIO] setIsSpeaking(true) - First chunk starting at ${x.toFixed(
|
|
961
975
|
3
|
|
962
976
|
)}`
|
|
963
|
-
), b.current =
|
|
964
|
-
const
|
|
965
|
-
|
|
966
|
-
`[AUDIO] Response started. Initial startTime: ${
|
|
977
|
+
), b.current = x;
|
|
978
|
+
const D = (x - N) * 1e3;
|
|
979
|
+
q.current = performance.now() + D, W(
|
|
980
|
+
`[AUDIO] Response started. Initial startTime: ${x.toFixed(
|
|
967
981
|
3
|
|
968
|
-
)}, CT: ${
|
|
982
|
+
)}, CT: ${N.toFixed(3)}`
|
|
969
983
|
);
|
|
970
984
|
}
|
|
971
|
-
|
|
972
|
-
const
|
|
973
|
-
i && (
|
|
974
|
-
`[AUDIO] New segment detected at +${
|
|
985
|
+
B.start(x);
|
|
986
|
+
const K = (x - b.current) * 1e3;
|
|
987
|
+
i && (de.current = K, W(
|
|
988
|
+
`[AUDIO] New segment detected at +${K.toFixed(
|
|
975
989
|
0
|
|
976
990
|
)}ms. Resetting segment offset.`
|
|
977
|
-
)), t.forEach((
|
|
978
|
-
const
|
|
979
|
-
if (
|
|
980
|
-
const
|
|
981
|
-
|
|
982
|
-
`[AUDIO] Viseme "${
|
|
991
|
+
)), t.forEach((D, re) => {
|
|
992
|
+
const E = D.symbol ?? "";
|
|
993
|
+
if (E) {
|
|
994
|
+
const se = Zt(E), le = Math.round(D.start * 1e3), Se = Math.round((D.duration ?? 0) * 1e3), ut = de.current + le;
|
|
995
|
+
re < 3 && W(
|
|
996
|
+
`[AUDIO] Viseme "${E}": segment_relative=${le}ms, segment_offset=${de.current.toFixed(
|
|
983
997
|
0
|
|
984
|
-
)}ms => vtime=${
|
|
985
|
-
),
|
|
998
|
+
)}ms => vtime=${ut}ms`
|
|
999
|
+
), se.forEach((dt) => {
|
|
986
1000
|
m.current.push({
|
|
987
|
-
viseme:
|
|
988
|
-
weight:
|
|
989
|
-
vtime:
|
|
990
|
-
vduration:
|
|
1001
|
+
viseme: dt.v,
|
|
1002
|
+
weight: dt.w,
|
|
1003
|
+
vtime: ut,
|
|
1004
|
+
vduration: Se
|
|
991
1005
|
});
|
|
992
1006
|
});
|
|
993
1007
|
}
|
|
994
|
-
}),
|
|
1008
|
+
}), _("Speaking...");
|
|
995
1009
|
} finally {
|
|
996
|
-
if (
|
|
997
|
-
const
|
|
998
|
-
|
|
1010
|
+
if (me.current = !1, ae.current.length > 0) {
|
|
1011
|
+
const l = ae.current.shift();
|
|
1012
|
+
l && Ke(l.audio, l.visemes, l.isNewSegment);
|
|
999
1013
|
}
|
|
1000
1014
|
}
|
|
1001
1015
|
}
|
|
1002
|
-
},
|
|
1016
|
+
}, Tt = async (e) => {
|
|
1003
1017
|
try {
|
|
1004
|
-
|
|
1005
|
-
const t = await e.arrayBuffer(),
|
|
1006
|
-
|
|
1007
|
-
const
|
|
1008
|
-
Ve(),
|
|
1009
|
-
const
|
|
1018
|
+
O(!0), Me.current = "", oe(""), _("Processing Voice...");
|
|
1019
|
+
const t = await e.arrayBuffer(), l = await new (window.AudioContext || window.webkitAudioContext)().decodeAudioData(t), r = Lt(l), a = new FileReader();
|
|
1020
|
+
a.readAsDataURL(r), a.onloadend = async () => {
|
|
1021
|
+
const w = a.result.split(",")[1];
|
|
1022
|
+
Ve(), R(""), fe.current = "", Te.current = !1;
|
|
1023
|
+
const T = `${ht}/stt?token=${encodeURIComponent(
|
|
1010
1024
|
p
|
|
1011
|
-
)}`,
|
|
1025
|
+
)}`, N = await fetch(T, {
|
|
1012
1026
|
method: "POST",
|
|
1013
1027
|
headers: { "Content-Type": "application/json" },
|
|
1014
1028
|
body: JSON.stringify({
|
|
1015
|
-
audio_base64:
|
|
1029
|
+
audio_base64: w,
|
|
1016
1030
|
audio_format: "wav"
|
|
1017
1031
|
})
|
|
1018
1032
|
});
|
|
1019
|
-
if (
|
|
1020
|
-
const fe = await P.text();
|
|
1021
|
-
let C = "STT Failed";
|
|
1033
|
+
if (N.status === 429) {
|
|
1022
1034
|
try {
|
|
1023
|
-
|
|
1035
|
+
const re = await N.text(), E = JSON.parse(re);
|
|
1036
|
+
W("[STT] 429 agent at capacity:", E?.detail);
|
|
1024
1037
|
} catch {
|
|
1025
|
-
fe && (C = fe.slice(0, 200));
|
|
1026
1038
|
}
|
|
1027
|
-
|
|
1039
|
+
R(""), _("Busy"), O(!1);
|
|
1040
|
+
return;
|
|
1028
1041
|
}
|
|
1029
|
-
|
|
1030
|
-
|
|
1031
|
-
|
|
1042
|
+
if (!N.ok) {
|
|
1043
|
+
const re = await N.text();
|
|
1044
|
+
let E = "STT Failed";
|
|
1045
|
+
try {
|
|
1046
|
+
E = JSON.parse(re).error || E;
|
|
1047
|
+
} catch {
|
|
1048
|
+
re && (E = re.slice(0, 200));
|
|
1049
|
+
}
|
|
1050
|
+
throw new Error(E);
|
|
1051
|
+
}
|
|
1052
|
+
const x = N.body;
|
|
1053
|
+
if (W("this is body" + x), !x) {
|
|
1054
|
+
_("STT Failed"), O(!1);
|
|
1032
1055
|
return;
|
|
1033
1056
|
}
|
|
1034
|
-
const
|
|
1035
|
-
|
|
1036
|
-
const
|
|
1037
|
-
let V = "",
|
|
1038
|
-
const
|
|
1039
|
-
switch (
|
|
1057
|
+
const C = x.getReader();
|
|
1058
|
+
ne.current = !1;
|
|
1059
|
+
const B = new TextDecoder();
|
|
1060
|
+
let V = "", K = !1;
|
|
1061
|
+
const D = async (re, E) => {
|
|
1062
|
+
switch (re) {
|
|
1040
1063
|
case "transcript":
|
|
1041
|
-
|
|
1064
|
+
E.transcript != null && R(String(E.transcript));
|
|
1042
1065
|
break;
|
|
1043
1066
|
case "text": {
|
|
1044
|
-
const
|
|
1045
|
-
|
|
1067
|
+
const se = E.delta ?? E.text ?? "";
|
|
1068
|
+
se && rt(se);
|
|
1046
1069
|
break;
|
|
1047
1070
|
}
|
|
1048
1071
|
case "audio": {
|
|
1049
|
-
const
|
|
1050
|
-
|
|
1072
|
+
const se = E.chunk, le = E.visemes ?? [], Se = !!E.is_new_segment;
|
|
1073
|
+
se && await Ke(se, le, Se);
|
|
1051
1074
|
break;
|
|
1052
1075
|
}
|
|
1053
1076
|
case "done": {
|
|
1054
|
-
|
|
1077
|
+
K = !0, _("Ready"), O(!1);
|
|
1055
1078
|
break;
|
|
1056
1079
|
}
|
|
1057
1080
|
case "error": {
|
|
1058
|
-
|
|
1081
|
+
K = !0, _("STT Failed"), O(!1);
|
|
1059
1082
|
break;
|
|
1060
1083
|
}
|
|
1061
1084
|
default:
|
|
@@ -1063,93 +1086,93 @@ const en = ({
|
|
|
1063
1086
|
}
|
|
1064
1087
|
};
|
|
1065
1088
|
for (; ; ) {
|
|
1066
|
-
const { done:
|
|
1067
|
-
|
|
1068
|
-
const
|
|
1089
|
+
const { done: re, value: E } = await C.read();
|
|
1090
|
+
E && (V += B.decode(E, { stream: !0 }));
|
|
1091
|
+
const se = V.split(`
|
|
1069
1092
|
|
|
1070
1093
|
`);
|
|
1071
|
-
V =
|
|
1072
|
-
for (const
|
|
1073
|
-
const
|
|
1074
|
-
|
|
1094
|
+
V = se.pop() ?? "";
|
|
1095
|
+
for (const le of se) {
|
|
1096
|
+
const Se = He(le);
|
|
1097
|
+
Se && await D(Se.event, Se.data);
|
|
1075
1098
|
}
|
|
1076
|
-
if (
|
|
1099
|
+
if (re) {
|
|
1077
1100
|
if (V.trim()) {
|
|
1078
|
-
const
|
|
1079
|
-
|
|
1101
|
+
const le = He(V.trim());
|
|
1102
|
+
le && await D(le.event, le.data);
|
|
1080
1103
|
}
|
|
1081
|
-
|
|
1104
|
+
K || (_("Ready"), O(!1));
|
|
1082
1105
|
break;
|
|
1083
1106
|
}
|
|
1084
1107
|
}
|
|
1085
1108
|
};
|
|
1086
1109
|
} catch (t) {
|
|
1087
|
-
console.error("Audio Submission Error:", t),
|
|
1110
|
+
console.error("Audio Submission Error:", t), _("STT Failed"), O(!1);
|
|
1088
1111
|
}
|
|
1089
|
-
},
|
|
1090
|
-
e && e.preventDefault(),
|
|
1091
|
-
},
|
|
1112
|
+
}, Mt = async (e) => {
|
|
1113
|
+
e && e.preventDefault(), Me.current = "", oe(""), !(!I || ee) && await Et(I);
|
|
1114
|
+
}, He = (e) => {
|
|
1092
1115
|
const t = e.split(/\r?\n/);
|
|
1093
|
-
let i = "",
|
|
1094
|
-
for (const
|
|
1095
|
-
|
|
1116
|
+
let i = "", l = "";
|
|
1117
|
+
for (const a of t)
|
|
1118
|
+
a.startsWith("event:") ? i = a.slice(6).trim() : a.startsWith("data:") && (l = a.slice(5).trim());
|
|
1096
1119
|
if (!i) return null;
|
|
1097
1120
|
let r = {};
|
|
1098
|
-
if (
|
|
1121
|
+
if (l)
|
|
1099
1122
|
try {
|
|
1100
|
-
r = JSON.parse(
|
|
1123
|
+
r = JSON.parse(l);
|
|
1101
1124
|
} catch {
|
|
1102
|
-
r = { raw:
|
|
1125
|
+
r = { raw: l };
|
|
1103
1126
|
}
|
|
1104
1127
|
return { event: i, data: r };
|
|
1105
|
-
},
|
|
1128
|
+
}, ct = (e, t) => {
|
|
1106
1129
|
switch (e) {
|
|
1107
1130
|
case "connected":
|
|
1108
|
-
|
|
1131
|
+
fe.current = "", Te.current = !1;
|
|
1109
1132
|
break;
|
|
1110
1133
|
case "text": {
|
|
1111
1134
|
const i = t.delta ?? "";
|
|
1112
|
-
i &&
|
|
1135
|
+
i && rt(i);
|
|
1113
1136
|
break;
|
|
1114
1137
|
}
|
|
1115
1138
|
case "audio": {
|
|
1116
|
-
const i = t.chunk,
|
|
1117
|
-
i &&
|
|
1139
|
+
const i = t.chunk, l = t.visemes ?? [];
|
|
1140
|
+
i && Ke(i, l);
|
|
1118
1141
|
break;
|
|
1119
1142
|
}
|
|
1120
1143
|
case "done": {
|
|
1121
|
-
const i =
|
|
1144
|
+
const i = st(), l = Me.current.trim(), r = [
|
|
1122
1145
|
...i,
|
|
1123
|
-
{ role: "user", content:
|
|
1124
|
-
{ role: "assistant", content:
|
|
1146
|
+
{ role: "user", content: I || "..." },
|
|
1147
|
+
{ role: "assistant", content: l }
|
|
1125
1148
|
];
|
|
1126
|
-
|
|
1149
|
+
yt(r), S.current = [...m.current], _("Ready"), O(!1), R("");
|
|
1127
1150
|
break;
|
|
1128
1151
|
}
|
|
1129
1152
|
case "error": {
|
|
1130
1153
|
const i = t.message ?? "Unknown error";
|
|
1131
|
-
|
|
1154
|
+
Me.current = i, oe(i), _("Agent Failed"), O(!1);
|
|
1132
1155
|
break;
|
|
1133
1156
|
}
|
|
1134
1157
|
}
|
|
1135
|
-
},
|
|
1136
|
-
|
|
1137
|
-
const t = `${
|
|
1158
|
+
}, Et = async (e) => {
|
|
1159
|
+
O(!0), _("Thinking..."), Me.current = "", fe.current = "", Te.current = !1, Ve(), G.current = 0, Ue(0);
|
|
1160
|
+
const t = `${ht}/agent/chat?token=${encodeURIComponent(
|
|
1138
1161
|
p
|
|
1139
1162
|
)}`;
|
|
1140
1163
|
try {
|
|
1141
|
-
const i =
|
|
1142
|
-
let
|
|
1143
|
-
|
|
1164
|
+
const i = st();
|
|
1165
|
+
let l = sessionStorage.getItem("STREAMOJI_LEADS_SESSION_LEAD_ID");
|
|
1166
|
+
l || (Pt(
|
|
1144
1167
|
"[CHAT] Session UID missing at send time! Generating emergency backup."
|
|
1145
|
-
),
|
|
1168
|
+
), l = "emergency-" + Math.random().toString(36).substring(7), sessionStorage.setItem("STREAMOJI_LEADS_SESSION_LEAD_ID", l));
|
|
1146
1169
|
const r = {
|
|
1147
1170
|
history: i,
|
|
1148
1171
|
question: e,
|
|
1149
|
-
lead_id:
|
|
1172
|
+
lead_id: l
|
|
1150
1173
|
};
|
|
1151
|
-
|
|
1152
|
-
const
|
|
1174
|
+
W("[CHAT] Sending payload:", r);
|
|
1175
|
+
const a = await fetch(t, {
|
|
1153
1176
|
method: "POST",
|
|
1154
1177
|
headers: {
|
|
1155
1178
|
"Content-Type": "application/json"
|
|
@@ -1157,69 +1180,78 @@ const en = ({
|
|
|
1157
1180
|
body: JSON.stringify(r),
|
|
1158
1181
|
cache: "default"
|
|
1159
1182
|
});
|
|
1160
|
-
if (
|
|
1183
|
+
if (a.status === 429) {
|
|
1184
|
+
try {
|
|
1185
|
+
const C = await a.json();
|
|
1186
|
+
W("[CHAT] 429 agent at capacity:", C?.detail);
|
|
1187
|
+
} catch {
|
|
1188
|
+
}
|
|
1189
|
+
R(""), _("Busy"), O(!1);
|
|
1190
|
+
return;
|
|
1191
|
+
}
|
|
1192
|
+
if (!a.ok)
|
|
1161
1193
|
throw new Error("Agent request failed");
|
|
1162
|
-
const
|
|
1163
|
-
if (!
|
|
1164
|
-
|
|
1194
|
+
const w = a.body;
|
|
1195
|
+
if (!w) {
|
|
1196
|
+
_("Agent Failed"), O(!1);
|
|
1165
1197
|
return;
|
|
1166
1198
|
}
|
|
1167
|
-
const
|
|
1168
|
-
|
|
1169
|
-
const
|
|
1170
|
-
let
|
|
1199
|
+
const T = w.getReader();
|
|
1200
|
+
ne.current = !1;
|
|
1201
|
+
const N = new TextDecoder();
|
|
1202
|
+
let x = "";
|
|
1171
1203
|
for (; ; ) {
|
|
1172
|
-
const { done:
|
|
1173
|
-
|
|
1174
|
-
`[SSE] Chunk received. done=${
|
|
1175
|
-
),
|
|
1176
|
-
const V =
|
|
1204
|
+
const { done: C, value: B } = await T.read();
|
|
1205
|
+
W(
|
|
1206
|
+
`[SSE] Chunk received. done=${C}, length=${B?.length || 0}`
|
|
1207
|
+
), B && (x += N.decode(B, { stream: !0 }));
|
|
1208
|
+
const V = x.split(`
|
|
1177
1209
|
|
|
1178
1210
|
`);
|
|
1179
|
-
|
|
1180
|
-
for (const
|
|
1181
|
-
|
|
1182
|
-
const
|
|
1183
|
-
|
|
1211
|
+
x = V.pop() ?? "";
|
|
1212
|
+
for (const K of V) {
|
|
1213
|
+
W(`[SSE] Processing block: ${K.slice(0, 50)}...`);
|
|
1214
|
+
const D = He(K);
|
|
1215
|
+
D && (W(`[SSE] Event: ${D.event}`), ct(D.event, D.data));
|
|
1184
1216
|
}
|
|
1185
|
-
if (
|
|
1186
|
-
if (
|
|
1187
|
-
const
|
|
1188
|
-
|
|
1217
|
+
if (C) {
|
|
1218
|
+
if (W("[SSE] Stream finished"), x.trim()) {
|
|
1219
|
+
const K = He(x.trim());
|
|
1220
|
+
K && ct(K.event, K.data);
|
|
1189
1221
|
}
|
|
1190
|
-
|
|
1222
|
+
_("Ready"), O(!1), R("");
|
|
1191
1223
|
break;
|
|
1192
1224
|
}
|
|
1193
1225
|
}
|
|
1194
1226
|
} catch (i) {
|
|
1195
|
-
console.error("Chat Error:", i),
|
|
1227
|
+
console.error("Chat Error:", i), _("Agent Failed"), O(!1);
|
|
1196
1228
|
}
|
|
1197
|
-
},
|
|
1229
|
+
}, lt = pe.trim(), Qe = lt && M ? lt.slice(
|
|
1198
1230
|
0,
|
|
1199
|
-
|
|
1231
|
+
ke != null && ke > 0 ? ke : 0
|
|
1200
1232
|
) : "";
|
|
1201
|
-
|
|
1202
|
-
const e =
|
|
1203
|
-
e !== "exiting" && (
|
|
1204
|
-
}, [
|
|
1205
|
-
const
|
|
1206
|
-
const e =
|
|
1207
|
-
e === "entering" ?
|
|
1233
|
+
H(() => {
|
|
1234
|
+
const e = qe.current;
|
|
1235
|
+
e !== "exiting" && (Qe ? (gt(Qe), e === "hidden" && We("entering")) : (e === "visible" || e === "entering") && We("exiting"));
|
|
1236
|
+
}, [Qe, Z]);
|
|
1237
|
+
const It = $e(() => {
|
|
1238
|
+
const e = qe.current;
|
|
1239
|
+
e === "entering" ? We("visible") : e === "exiting" && We("hidden");
|
|
1208
1240
|
}, []);
|
|
1209
|
-
return
|
|
1210
|
-
const e =
|
|
1241
|
+
return Nt(() => {
|
|
1242
|
+
const e = Le.current;
|
|
1211
1243
|
e && (e.scrollTop = e.scrollHeight);
|
|
1212
|
-
}, [
|
|
1213
|
-
/* @__PURE__ */
|
|
1214
|
-
|
|
1244
|
+
}, [nt]), /* @__PURE__ */ ie("div", { className: "avatar-widget-container", children: [
|
|
1245
|
+
/* @__PURE__ */ ie("div", { className: "avatar-input-area", children: [
|
|
1246
|
+
be !== "hidden" ? /* @__PURE__ */ c(
|
|
1215
1247
|
"div",
|
|
1216
1248
|
{
|
|
1217
|
-
className: `avatar-thinking-tab${
|
|
1218
|
-
onAnimationEnd:
|
|
1219
|
-
children:
|
|
1249
|
+
className: `avatar-thinking-tab${be === "exiting" ? " avatar-thinking-tab--exiting" : be === "entering" ? " avatar-thinking-tab--entering" : ""}`,
|
|
1250
|
+
onAnimationEnd: bt,
|
|
1251
|
+
children: Ce
|
|
1220
1252
|
}
|
|
1221
1253
|
) : null,
|
|
1222
|
-
/* @__PURE__ */
|
|
1254
|
+
/* @__PURE__ */ c("div", { className: "avatar-input-container", children: /* @__PURE__ */ c(
|
|
1223
1255
|
"div",
|
|
1224
1256
|
{
|
|
1225
1257
|
style: {
|
|
@@ -1228,15 +1260,15 @@ const en = ({
|
|
|
1228
1260
|
width: "100%",
|
|
1229
1261
|
height: "100%"
|
|
1230
1262
|
},
|
|
1231
|
-
children:
|
|
1232
|
-
/* @__PURE__ */
|
|
1263
|
+
children: Ge ? /* @__PURE__ */ ie("div", { className: "avatar-input-recording", children: [
|
|
1264
|
+
/* @__PURE__ */ c(
|
|
1233
1265
|
"button",
|
|
1234
1266
|
{
|
|
1235
1267
|
type: "button",
|
|
1236
1268
|
className: "avatar-recording-cancel",
|
|
1237
|
-
onClick:
|
|
1269
|
+
onClick: At,
|
|
1238
1270
|
title: "Cancel",
|
|
1239
|
-
children: /* @__PURE__ */
|
|
1271
|
+
children: /* @__PURE__ */ ie(
|
|
1240
1272
|
"svg",
|
|
1241
1273
|
{
|
|
1242
1274
|
width: "18",
|
|
@@ -1249,14 +1281,14 @@ const en = ({
|
|
|
1249
1281
|
strokeLinejoin: "round",
|
|
1250
1282
|
style: { display: "block" },
|
|
1251
1283
|
children: [
|
|
1252
|
-
/* @__PURE__ */
|
|
1253
|
-
/* @__PURE__ */
|
|
1284
|
+
/* @__PURE__ */ c("line", { x1: "18", y1: "6", x2: "6", y2: "18" }),
|
|
1285
|
+
/* @__PURE__ */ c("line", { x1: "6", y1: "6", x2: "18", y2: "18" })
|
|
1254
1286
|
]
|
|
1255
1287
|
}
|
|
1256
1288
|
)
|
|
1257
1289
|
}
|
|
1258
1290
|
),
|
|
1259
|
-
/* @__PURE__ */
|
|
1291
|
+
/* @__PURE__ */ ie(
|
|
1260
1292
|
"div",
|
|
1261
1293
|
{
|
|
1262
1294
|
style: {
|
|
@@ -1268,8 +1300,8 @@ const en = ({
|
|
|
1268
1300
|
minWidth: 0
|
|
1269
1301
|
},
|
|
1270
1302
|
children: [
|
|
1271
|
-
/* @__PURE__ */
|
|
1272
|
-
/* @__PURE__ */
|
|
1303
|
+
/* @__PURE__ */ c("div", { style: { flex: 1, height: "100%" }, children: /* @__PURE__ */ c(ft, { analyser: xt }) }),
|
|
1304
|
+
/* @__PURE__ */ ie(
|
|
1273
1305
|
"span",
|
|
1274
1306
|
{
|
|
1275
1307
|
style: {
|
|
@@ -1282,23 +1314,23 @@ const en = ({
|
|
|
1282
1314
|
fontVariantNumeric: "tabular-nums"
|
|
1283
1315
|
},
|
|
1284
1316
|
children: [
|
|
1285
|
-
Math.floor(
|
|
1317
|
+
Math.floor(it / 60),
|
|
1286
1318
|
":",
|
|
1287
|
-
String(
|
|
1319
|
+
String(it % 60).padStart(2, "0")
|
|
1288
1320
|
]
|
|
1289
1321
|
}
|
|
1290
1322
|
)
|
|
1291
1323
|
]
|
|
1292
1324
|
}
|
|
1293
1325
|
),
|
|
1294
|
-
/* @__PURE__ */
|
|
1326
|
+
/* @__PURE__ */ c(
|
|
1295
1327
|
"button",
|
|
1296
1328
|
{
|
|
1297
1329
|
type: "button",
|
|
1298
1330
|
className: "avatar-recording-confirm",
|
|
1299
|
-
onClick:
|
|
1331
|
+
onClick: Rt,
|
|
1300
1332
|
title: "Send",
|
|
1301
|
-
children: /* @__PURE__ */
|
|
1333
|
+
children: /* @__PURE__ */ c(
|
|
1302
1334
|
"svg",
|
|
1303
1335
|
{
|
|
1304
1336
|
width: "18",
|
|
@@ -1310,13 +1342,13 @@ const en = ({
|
|
|
1310
1342
|
strokeLinecap: "round",
|
|
1311
1343
|
strokeLinejoin: "round",
|
|
1312
1344
|
style: { display: "block" },
|
|
1313
|
-
children: /* @__PURE__ */
|
|
1345
|
+
children: /* @__PURE__ */ c("polyline", { points: "20 6 9 17 4 12" })
|
|
1314
1346
|
}
|
|
1315
1347
|
)
|
|
1316
1348
|
}
|
|
1317
1349
|
)
|
|
1318
|
-
] }) :
|
|
1319
|
-
/* @__PURE__ */
|
|
1350
|
+
] }) : M ? /* @__PURE__ */ ie("div", { className: "avatar-input-speaking", children: [
|
|
1351
|
+
/* @__PURE__ */ c(
|
|
1320
1352
|
"div",
|
|
1321
1353
|
{
|
|
1322
1354
|
style: {
|
|
@@ -1326,20 +1358,20 @@ const en = ({
|
|
|
1326
1358
|
alignItems: "center",
|
|
1327
1359
|
paddingRight: "8px"
|
|
1328
1360
|
},
|
|
1329
|
-
children: /* @__PURE__ */
|
|
1361
|
+
children: /* @__PURE__ */ c(ft, { analyser: at })
|
|
1330
1362
|
}
|
|
1331
1363
|
),
|
|
1332
|
-
/* @__PURE__ */
|
|
1364
|
+
/* @__PURE__ */ c(
|
|
1333
1365
|
"button",
|
|
1334
1366
|
{
|
|
1335
1367
|
type: "button",
|
|
1336
1368
|
className: "avatar-speaking-stop",
|
|
1337
1369
|
onClick: () => Ve(!0),
|
|
1338
1370
|
title: "Stop",
|
|
1339
|
-
children: /* @__PURE__ */
|
|
1371
|
+
children: /* @__PURE__ */ c("span", { className: "avatar-speaking-stop__icon", "aria-hidden": !0 })
|
|
1340
1372
|
}
|
|
1341
1373
|
)
|
|
1342
|
-
] }) :
|
|
1374
|
+
] }) : ee ? /* @__PURE__ */ c(
|
|
1343
1375
|
"div",
|
|
1344
1376
|
{
|
|
1345
1377
|
style: {
|
|
@@ -1349,12 +1381,12 @@ const en = ({
|
|
|
1349
1381
|
alignItems: "center",
|
|
1350
1382
|
justifyContent: "center"
|
|
1351
1383
|
},
|
|
1352
|
-
children: /* @__PURE__ */
|
|
1384
|
+
children: /* @__PURE__ */ c("div", { className: "avatar-input-loader" })
|
|
1353
1385
|
}
|
|
1354
|
-
) : /* @__PURE__ */
|
|
1386
|
+
) : /* @__PURE__ */ ie(
|
|
1355
1387
|
"form",
|
|
1356
1388
|
{
|
|
1357
|
-
onSubmit:
|
|
1389
|
+
onSubmit: Mt,
|
|
1358
1390
|
style: {
|
|
1359
1391
|
flex: 1,
|
|
1360
1392
|
display: "flex",
|
|
@@ -1362,28 +1394,55 @@ const en = ({
|
|
|
1362
1394
|
alignItems: "center"
|
|
1363
1395
|
},
|
|
1364
1396
|
children: [
|
|
1365
|
-
/* @__PURE__ */
|
|
1397
|
+
/* @__PURE__ */ c(
|
|
1366
1398
|
"input",
|
|
1367
1399
|
{
|
|
1368
1400
|
id: "avatar-text-input",
|
|
1369
1401
|
type: "text",
|
|
1370
|
-
value:
|
|
1371
|
-
onChange: (e) =>
|
|
1372
|
-
placeholder: "Ask me anything",
|
|
1373
|
-
disabled:
|
|
1402
|
+
value: I,
|
|
1403
|
+
onChange: (e) => R(e.target.value),
|
|
1404
|
+
placeholder: y === "Busy" ? "Assisting another user" : "Ask me anything",
|
|
1405
|
+
disabled: ee || y === "Busy",
|
|
1374
1406
|
autoComplete: "off",
|
|
1375
1407
|
style: { width: "100%", height: "100%" }
|
|
1376
1408
|
}
|
|
1377
1409
|
),
|
|
1378
|
-
|
|
1410
|
+
y === "Busy" ? /* @__PURE__ */ c(
|
|
1411
|
+
"button",
|
|
1412
|
+
{
|
|
1413
|
+
type: "button",
|
|
1414
|
+
className: "mic-button",
|
|
1415
|
+
disabled: !0,
|
|
1416
|
+
style: { backgroundColor: "#1e4a5e" },
|
|
1417
|
+
title: "Agent at capacity",
|
|
1418
|
+
children: /* @__PURE__ */ c(
|
|
1419
|
+
"svg",
|
|
1420
|
+
{
|
|
1421
|
+
width: "24",
|
|
1422
|
+
height: "24",
|
|
1423
|
+
viewBox: "0 0 24 24",
|
|
1424
|
+
fill: "none",
|
|
1425
|
+
xmlns: "http://www.w3.org/2000/svg",
|
|
1426
|
+
"aria-hidden": "true",
|
|
1427
|
+
children: /* @__PURE__ */ c(
|
|
1428
|
+
"path",
|
|
1429
|
+
{
|
|
1430
|
+
d: "M4 2L20 2L12 10L4 2z M12 14L4 22L20 22L12 14z",
|
|
1431
|
+
fill: "white"
|
|
1432
|
+
}
|
|
1433
|
+
)
|
|
1434
|
+
}
|
|
1435
|
+
)
|
|
1436
|
+
}
|
|
1437
|
+
) : I.trim() === "" ? /* @__PURE__ */ c(
|
|
1379
1438
|
"button",
|
|
1380
1439
|
{
|
|
1381
1440
|
type: "button",
|
|
1382
1441
|
className: "mic-button",
|
|
1383
|
-
onClick:
|
|
1384
|
-
disabled:
|
|
1442
|
+
onClick: kt,
|
|
1443
|
+
disabled: ee,
|
|
1385
1444
|
style: { backgroundColor: "#1e4a5e" },
|
|
1386
|
-
children: /* @__PURE__ */
|
|
1445
|
+
children: /* @__PURE__ */ ie(
|
|
1387
1446
|
"svg",
|
|
1388
1447
|
{
|
|
1389
1448
|
width: "28",
|
|
@@ -1392,14 +1451,14 @@ const en = ({
|
|
|
1392
1451
|
fill: "none",
|
|
1393
1452
|
xmlns: "http://www.w3.org/2000/svg",
|
|
1394
1453
|
children: [
|
|
1395
|
-
/* @__PURE__ */
|
|
1454
|
+
/* @__PURE__ */ c(
|
|
1396
1455
|
"path",
|
|
1397
1456
|
{
|
|
1398
1457
|
d: "M12 14C13.66 14 15 12.66 15 11V5C15 3.34 13.66 2 12 2C10.34 2 9 3.34 9 5V11C9 12.66 10.34 14 12 14Z",
|
|
1399
1458
|
fill: "white"
|
|
1400
1459
|
}
|
|
1401
1460
|
),
|
|
1402
|
-
/* @__PURE__ */
|
|
1461
|
+
/* @__PURE__ */ c(
|
|
1403
1462
|
"path",
|
|
1404
1463
|
{
|
|
1405
1464
|
d: "M17 11C17 13.76 14.76 16 12 16C9.24 16 7 13.76 7 11H5C5 14.53 7.61 17.43 11 17.93V21H13V17.93C16.39 17.43 19 14.53 19 11H17Z",
|
|
@@ -1410,15 +1469,34 @@ const en = ({
|
|
|
1410
1469
|
}
|
|
1411
1470
|
)
|
|
1412
1471
|
}
|
|
1413
|
-
) : /* @__PURE__ */
|
|
1472
|
+
) : /* @__PURE__ */ c(
|
|
1414
1473
|
"button",
|
|
1415
1474
|
{
|
|
1416
1475
|
type: "submit",
|
|
1417
1476
|
className: "mic-button",
|
|
1418
|
-
disabled:
|
|
1477
|
+
disabled: ee,
|
|
1419
1478
|
style: { backgroundColor: "#1e4a5e" },
|
|
1420
1479
|
title: "Send",
|
|
1421
|
-
children: /* @__PURE__ */
|
|
1480
|
+
children: /* @__PURE__ */ c(
|
|
1481
|
+
"svg",
|
|
1482
|
+
{
|
|
1483
|
+
width: 24,
|
|
1484
|
+
height: 24,
|
|
1485
|
+
viewBox: "0 0 24 24",
|
|
1486
|
+
fill: "none",
|
|
1487
|
+
"aria-hidden": "true",
|
|
1488
|
+
children: /* @__PURE__ */ c(
|
|
1489
|
+
"path",
|
|
1490
|
+
{
|
|
1491
|
+
d: "M19 12H5M19 12L14 17M19 12L14 7",
|
|
1492
|
+
stroke: "white",
|
|
1493
|
+
strokeWidth: "2",
|
|
1494
|
+
strokeLinecap: "round",
|
|
1495
|
+
strokeLinejoin: "round"
|
|
1496
|
+
}
|
|
1497
|
+
)
|
|
1498
|
+
}
|
|
1499
|
+
)
|
|
1422
1500
|
}
|
|
1423
1501
|
)
|
|
1424
1502
|
]
|
|
@@ -1427,22 +1505,22 @@ const en = ({
|
|
|
1427
1505
|
}
|
|
1428
1506
|
) })
|
|
1429
1507
|
] }),
|
|
1430
|
-
/* @__PURE__ */
|
|
1431
|
-
|
|
1508
|
+
/* @__PURE__ */ c("div", { className: "avatar-wrapper", children: /* @__PURE__ */ ie("div", { className: "avatar-scene-wrapper", children: [
|
|
1509
|
+
Z !== "hidden" && /* @__PURE__ */ c(
|
|
1432
1510
|
"div",
|
|
1433
1511
|
{
|
|
1434
|
-
className: `avatar-bubble${
|
|
1435
|
-
onAnimationEnd:
|
|
1436
|
-
children: /* @__PURE__ */
|
|
1512
|
+
className: `avatar-bubble${Z === "entering" ? " avatar-bubble--entering" : Z === "exiting" ? " avatar-bubble--exiting" : ""}`,
|
|
1513
|
+
onAnimationEnd: It,
|
|
1514
|
+
children: /* @__PURE__ */ c("div", { ref: Le, className: "avatar-bubble__content", children: nt })
|
|
1437
1515
|
}
|
|
1438
1516
|
),
|
|
1439
|
-
/* @__PURE__ */
|
|
1517
|
+
/* @__PURE__ */ c(
|
|
1440
1518
|
"div",
|
|
1441
1519
|
{
|
|
1442
1520
|
className: "avatar-canvas-layer",
|
|
1443
|
-
style: { width:
|
|
1444
|
-
children: /* @__PURE__ */
|
|
1445
|
-
|
|
1521
|
+
style: { width: te, height: te },
|
|
1522
|
+
children: /* @__PURE__ */ ie(
|
|
1523
|
+
Ot,
|
|
1446
1524
|
{
|
|
1447
1525
|
shadows: !0,
|
|
1448
1526
|
camera: { position: [0.2, 1.4, 3], fov: 42 },
|
|
@@ -1450,28 +1528,28 @@ const en = ({
|
|
|
1450
1528
|
dpr: 1.8,
|
|
1451
1529
|
style: { pointerEvents: "none", width: "100%", height: "100%" },
|
|
1452
1530
|
children: [
|
|
1453
|
-
/* @__PURE__ */
|
|
1454
|
-
/* @__PURE__ */
|
|
1455
|
-
/* @__PURE__ */
|
|
1456
|
-
/* @__PURE__ */
|
|
1457
|
-
/* @__PURE__ */
|
|
1458
|
-
|
|
1531
|
+
/* @__PURE__ */ c(en, { target: zt }),
|
|
1532
|
+
/* @__PURE__ */ c("ambientLight", { intensity: 0.7 }),
|
|
1533
|
+
/* @__PURE__ */ c("directionalLight", { position: [0, 2, 2], intensity: 1 }),
|
|
1534
|
+
/* @__PURE__ */ c(Ct, { preset: "city" }),
|
|
1535
|
+
/* @__PURE__ */ c(Wt, { fallback: null, children: U !== null && /* @__PURE__ */ c(
|
|
1536
|
+
tn,
|
|
1459
1537
|
{
|
|
1460
|
-
avatarUrl:
|
|
1461
|
-
isPlayingRef:
|
|
1538
|
+
avatarUrl: U,
|
|
1539
|
+
isPlayingRef: F,
|
|
1462
1540
|
visemeQueueRef: m,
|
|
1463
1541
|
audioContextRef: $,
|
|
1464
1542
|
responseAudioStartTimeRef: b,
|
|
1465
|
-
adjustments:
|
|
1466
|
-
mood:
|
|
1543
|
+
adjustments: Gt,
|
|
1544
|
+
mood: f,
|
|
1467
1545
|
expression: s,
|
|
1468
|
-
agentResponse:
|
|
1469
|
-
isSpeaking:
|
|
1470
|
-
nextStartTimeRef:
|
|
1546
|
+
agentResponse: pe,
|
|
1547
|
+
isSpeaking: M,
|
|
1548
|
+
nextStartTimeRef: Q,
|
|
1471
1549
|
stopPlayback: Ve,
|
|
1472
|
-
setIsSpeaking:
|
|
1550
|
+
setIsSpeaking: ue,
|
|
1473
1551
|
expressionUrl: h,
|
|
1474
|
-
onExpressionFinished:
|
|
1552
|
+
onExpressionFinished: vt
|
|
1475
1553
|
}
|
|
1476
1554
|
) })
|
|
1477
1555
|
]
|
|
@@ -1481,17 +1559,17 @@ const en = ({
|
|
|
1481
1559
|
)
|
|
1482
1560
|
] }) })
|
|
1483
1561
|
] });
|
|
1484
|
-
},
|
|
1485
|
-
token:
|
|
1486
|
-
onNavigationRequested:
|
|
1487
|
-
}) => /* @__PURE__ */
|
|
1488
|
-
|
|
1562
|
+
}, un = ({
|
|
1563
|
+
token: d,
|
|
1564
|
+
onNavigationRequested: A
|
|
1565
|
+
}) => /* @__PURE__ */ c(
|
|
1566
|
+
rn,
|
|
1489
1567
|
{
|
|
1490
|
-
token:
|
|
1491
|
-
onNavigationRequested:
|
|
1568
|
+
token: d,
|
|
1569
|
+
onNavigationRequested: A
|
|
1492
1570
|
}
|
|
1493
1571
|
);
|
|
1494
1572
|
export {
|
|
1495
|
-
|
|
1573
|
+
un as AvatarWidget
|
|
1496
1574
|
};
|
|
1497
1575
|
//# sourceMappingURL=avatar-widget.js.map
|