@burdenoff/fe-libs 2026.1004.7 → 2026.1005.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/shared/assistant/api.d.ts +18 -0
- package/dist/shared/assistant/api.d.ts.map +1 -1
- package/dist/shared/assistant/api.js +169 -147
- package/dist/shared/assistant/capabilities.d.ts +21 -0
- package/dist/shared/assistant/capabilities.d.ts.map +1 -1
- package/dist/shared/assistant/capabilities.js +11 -1
- package/dist/shared/assistant/index.d.ts +5 -0
- package/dist/shared/assistant/index.d.ts.map +1 -1
- package/dist/shared/assistant/liveDeltas.d.ts +76 -0
- package/dist/shared/assistant/liveDeltas.d.ts.map +1 -0
- package/dist/shared/assistant/liveDeltas.js +196 -0
- package/dist/shared/assistant/liveOverlay.d.ts +62 -0
- package/dist/shared/assistant/liveOverlay.d.ts.map +1 -0
- package/dist/shared/assistant/liveOverlay.js +64 -0
- package/dist/shared/assistant/snapshotPoller.d.ts +48 -0
- package/dist/shared/assistant/snapshotPoller.d.ts.map +1 -0
- package/dist/shared/assistant/snapshotPoller.js +58 -0
- package/dist/shared/assistant/turnStream.d.ts +71 -0
- package/dist/shared/assistant/turnStream.d.ts.map +1 -0
- package/dist/shared/assistant/turnStream.js +266 -0
- package/dist/shared/assistant/turnTimeline.d.ts +27 -2
- package/dist/shared/assistant/turnTimeline.d.ts.map +1 -1
- package/dist/shared/assistant/turnTimeline.js +17 -28
- package/dist/shared/assistant/types.d.ts +10 -0
- package/dist/shared/assistant/types.d.ts.map +1 -1
- package/dist/shared/assistant/ui/AssistantChatArea.d.ts.map +1 -1
- package/dist/shared/assistant/ui/AssistantChatArea.js +1049 -1008
- package/dist/shared/assistant/ui/AssistantMessageList.d.ts +2 -0
- package/dist/shared/assistant/ui/AssistantMessageList.d.ts.map +1 -1
- package/dist/shared/assistant/ui/AssistantMessageList.js +48 -32
- package/dist/shared/assistant/ui/useVoiceSession.d.ts.map +1 -1
- package/dist/shared/assistant/ui/useVoiceSession.js +96 -93
- package/dist/shared/assistant/voice/affirmations.d.ts +44 -0
- package/dist/shared/assistant/voice/affirmations.d.ts.map +1 -0
- package/dist/shared/assistant/voice/affirmations.js +238 -0
- package/dist/shared/assistant/voice/handsFree.d.ts +16 -3
- package/dist/shared/assistant/voice/handsFree.d.ts.map +1 -1
- package/dist/shared/assistant/voice/handsFree.js +43 -37
- package/dist/shared/assistant/voice/voiceSession.d.ts +2 -0
- package/dist/shared/assistant/voice/voiceSession.d.ts.map +1 -1
- package/dist/shared/assistant/voice/voiceSession.js +3 -1
- package/dist/shared-assistant.js +208 -203
- package/package.json +1 -1
|
@@ -49,6 +49,8 @@ interface Props {
|
|
|
49
49
|
*/
|
|
50
50
|
hidesLegacyWriteCard?: (message: Message) => boolean;
|
|
51
51
|
}
|
|
52
|
+
/** At most one auto-scroll per this long while a reply is streaming in live. */
|
|
53
|
+
export declare const LIVE_SCROLL_GAP_MS = 250;
|
|
52
54
|
export declare const AssistantMessageList: FC<Props>;
|
|
53
55
|
export {};
|
|
54
56
|
//# sourceMappingURL=AssistantMessageList.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AssistantMessageList.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/AssistantMessageList.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAqB,KAAK,EAAE,EAAE,KAAK,SAAS,EAAE,MAAM,OAAO,CAAC;AAGnE,OAAO,KAAK,EAAE,+BAA+B,EAAE,OAAO,EAAE,MAAM,iBAAiB,CAAC;
|
|
1
|
+
{"version":3,"file":"AssistantMessageList.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/AssistantMessageList.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAqB,KAAK,EAAE,EAAE,KAAK,SAAS,EAAE,MAAM,OAAO,CAAC;AAGnE,OAAO,KAAK,EAAE,+BAA+B,EAAE,OAAO,EAAE,MAAM,iBAAiB,CAAC;AAShF,UAAU,KAAK;IACb;;;OAGG;IACH,qBAAqB,CAAC,EAAE,CAAC,SAAS,EAAE,MAAM,KAAK,IAAI,CAAC;IACpD,iBAAiB,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAClC;;;;;;OAMG;IACH,mBAAmB,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACpC;;;OAGG;IACH,kBAAkB,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACnC,QAAQ,EAAE,OAAO,EAAE,CAAC;IACpB;;;;OAIG;IACH,UAAU,CAAC,EAAE,+BAA+B,GAAG,IAAI,CAAC;IACpD,kBAAkB,EAAE,MAAM,GAAG,IAAI,CAAC;IAClC,mEAAmE;IACnE,eAAe,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAChC;;;;OAIG;IACH,OAAO,CAAC,EAAE,MAAM,IAAI,CAAC;IACrB;;;;OAIG;IACH,oBAAoB,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,KAAK,SAAS,CAAC;IACvD;;;;OAIG;IACH,oBAAoB,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,KAAK,OAAO,CAAC;CACtD;AAED,gFAAgF;AAChF,eAAO,MAAM,kBAAkB,MAAM,CAAC;AAEtC,eAAO,MAAM,oBAAoB,EAAE,EAAE,CAAC,KAAK,CAyJ1C,CAAC"}
|
|
@@ -2,50 +2,66 @@ import { useAssistantTr as e } from "../i18n.js";
|
|
|
2
2
|
import { approvalFollowUpReplyIds as t, approvedPendingWriteIds as n, goAheadSentReplyIds as r } from "../liveTurns.js";
|
|
3
3
|
import { readReducedMotion as i } from "./usePrefersReducedMotion.js";
|
|
4
4
|
import { AssistantMessageItem as a } from "./AssistantMessageItem.js";
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
5
|
+
import { useLiveOverlay as o } from "../liveOverlay.js";
|
|
6
|
+
import { useEffect as s, useRef as c } from "react";
|
|
7
|
+
import { jsx as l, jsxs as u } from "react/jsx-runtime";
|
|
7
8
|
//#region src/shared/assistant/ui/AssistantMessageList.tsx
|
|
8
|
-
var
|
|
9
|
-
let
|
|
10
|
-
for (let e =
|
|
9
|
+
var d = 250, f = ({ onApprovePendingWrite: d, approvingWriteRef: f = null, approvableMessageId: p = null, retryableMessageId: m = null, messages: h, processing: g, streamingMessageId: _, failedMessageId: v, onRetry: y, renderWriteProposals: b, hidesLegacyWriteCard: x }) => {
|
|
10
|
+
let S = e(), C = (() => {
|
|
11
|
+
for (let e = h.length - 1; e >= 0; --e) if (h[e].role === "assistant") return h[e].id;
|
|
11
12
|
return null;
|
|
12
|
-
})(),
|
|
13
|
-
|
|
14
|
-
let e =
|
|
13
|
+
})(), w = n(h), T = r(h), E = t(h), D = c(null), O = c(null);
|
|
14
|
+
s(() => {
|
|
15
|
+
let e = O.current;
|
|
15
16
|
if (e && e.scrollHeight - e.scrollTop - e.clientHeight < 100) {
|
|
16
17
|
let e = i();
|
|
17
|
-
|
|
18
|
+
D.current?.scrollIntoView({ behavior: e ? "auto" : "smooth" });
|
|
18
19
|
}
|
|
19
|
-
}, [
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
20
|
+
}, [h, _]);
|
|
21
|
+
let k = o((e) => e.byMessageId), A = _ === null ? null : k[_]?.content ?? null, j = c(0), M = c(null);
|
|
22
|
+
return s(() => {
|
|
23
|
+
if (A === null) return;
|
|
24
|
+
let e = () => {
|
|
25
|
+
M.current = null, j.current = Date.now();
|
|
26
|
+
let e = O.current;
|
|
27
|
+
e && e.scrollHeight - e.scrollTop - e.clientHeight < 100 && D.current?.scrollIntoView({ behavior: "auto" });
|
|
28
|
+
}, t = j.current + 250 - Date.now();
|
|
29
|
+
t <= 0 ? e() : M.current === null && (M.current = setTimeout(e, t));
|
|
30
|
+
}, [A]), s(() => () => {
|
|
31
|
+
M.current !== null && clearTimeout(M.current);
|
|
32
|
+
}, []), s(() => {
|
|
33
|
+
D.current?.scrollIntoView({ behavior: "instant" });
|
|
34
|
+
}, []), /* @__PURE__ */ u("div", {
|
|
35
|
+
ref: O,
|
|
23
36
|
className: "scrollbar-slim flex-1 space-y-4 overflow-y-auto p-3",
|
|
24
37
|
role: "log",
|
|
25
38
|
"aria-live": "polite",
|
|
26
39
|
"aria-relevant": "additions",
|
|
27
|
-
"aria-busy":
|
|
28
|
-
"aria-label":
|
|
29
|
-
children: [
|
|
30
|
-
let t =
|
|
31
|
-
return /* @__PURE__ */
|
|
32
|
-
onApprovePendingWrite: n ?
|
|
33
|
-
approvingWriteRef:
|
|
40
|
+
"aria-busy": _ !== null,
|
|
41
|
+
"aria-label": S("messageList.ariaLabel", "Conversation messages"),
|
|
42
|
+
children: [h.map((e) => {
|
|
43
|
+
let t = w.has(e.id), n = !t && (e.id === p || e.id === _);
|
|
44
|
+
return /* @__PURE__ */ l(a, {
|
|
45
|
+
onApprovePendingWrite: n ? d : void 0,
|
|
46
|
+
approvingWriteRef: f,
|
|
34
47
|
pendingWriteApproved: t,
|
|
35
|
-
pendingWriteGoAheadSent:
|
|
48
|
+
pendingWriteGoAheadSent: T.has(e.id),
|
|
36
49
|
pendingWriteExpired: !t && !n,
|
|
37
|
-
message: e
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
50
|
+
message: e.id === _ && A !== null ? {
|
|
51
|
+
...e,
|
|
52
|
+
content: A
|
|
53
|
+
} : e,
|
|
54
|
+
processing: g,
|
|
55
|
+
isStreaming: e.id === _,
|
|
56
|
+
isFailed: e.id === v,
|
|
57
|
+
isLastAssistant: e.id === m,
|
|
58
|
+
isNewestAssistant: e.id === C,
|
|
59
|
+
onRetry: E.has(e.id) ? void 0 : y,
|
|
60
|
+
legacyWriteCardHidden: x?.(e) ?? !1,
|
|
61
|
+
writeProposals: b?.(e)
|
|
46
62
|
}, e.id);
|
|
47
|
-
}), /* @__PURE__ */
|
|
63
|
+
}), /* @__PURE__ */ l("div", { ref: D })]
|
|
48
64
|
});
|
|
49
65
|
};
|
|
50
66
|
//#endregion
|
|
51
|
-
export {
|
|
67
|
+
export { f as AssistantMessageList, d as LIVE_SCROLL_GAP_MS };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"useVoiceSession.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/useVoiceSession.ts"],"names":[],"mappings":"AAUA,OAAO,EAAe,KAAK,eAAe,EAAE,MAAM,iBAAiB,CAAC;AAIpE,OAAO,EAGL,KAAK,YAAY,EAClB,MAAM,oBAAoB,CAAC;AAE5B,OAAO,EAgBL,KAAK,oBAAoB,EAE1B,MAAM,uBAAuB,CAAC;AAsC/B;;;;;;;;GAQG;AACH,MAAM,MAAM,kBAAkB,GAC5B,SAAS,GAAG,eAAe,GAAG,eAAe,GAAG,oBAAoB,CAAC;AAEvE;;;;;;;;GAQG;AACH,MAAM,WAAW,iBAAiB;IAChC,iFAAiF;IACjF,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,+DAA+D;IAC/D,IAAI,CAAC,EAAE,MAAM,CAAC;IACd;;;OAGG;IACH,WAAW,CAAC,EAAE,MAAM,OAAO,CAAC;CAC7B;AAMD,UAAU,OAAO;IACf,+EAA+E;IAC/E;;;;;;;OAOG;IACH,QAAQ,EAAE,CACR,IAAI,EAAE,MAAM,EACZ,cAAc,EAAE,MAAM;IACtB;;;OAGG;IACH,MAAM,EAAE,eAAe;IACvB;;;;;OAKG;IACH,IAAI,EAAE,eAAe,KAClB,IAAI,CAAC;IACV;;;;OAIG;IACH,WAAW,EAAE;QAAE,EAAE,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;IACjD,6EAA6E;IAC7E,QAAQ,EAAE,MAAM,CAAC;IACjB;;;OAGG;IACH,OAAO,CAAC,EAAE,YAAY,GAAG,MAAM,CAAC;IAChC;;;;;OAKG;IACH,WAAW,CAAC,EAAE,MAAM,IAAI,CAAC;CAC1B;AAED,oEAAoE;AACpE,MAAM,WAAW,eAAe;IAC9B,gEAAgE;IAChE,UAAU,EAAE,OAAO,CAAC;CACrB;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,eAAe,CAAC,EAC9B,QAAQ,EACR,WAAW,EACX,QAAQ,EACR,OAAO,EAAE,WAAW,EACpB,WAAW,GACZ,EAAE,OAAO;;
|
|
1
|
+
{"version":3,"file":"useVoiceSession.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/useVoiceSession.ts"],"names":[],"mappings":"AAUA,OAAO,EAAe,KAAK,eAAe,EAAE,MAAM,iBAAiB,CAAC;AAIpE,OAAO,EAGL,KAAK,YAAY,EAClB,MAAM,oBAAoB,CAAC;AAE5B,OAAO,EAgBL,KAAK,oBAAoB,EAE1B,MAAM,uBAAuB,CAAC;AAsC/B;;;;;;;;GAQG;AACH,MAAM,MAAM,kBAAkB,GAC5B,SAAS,GAAG,eAAe,GAAG,eAAe,GAAG,oBAAoB,CAAC;AAEvE;;;;;;;;GAQG;AACH,MAAM,WAAW,iBAAiB;IAChC,iFAAiF;IACjF,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,+DAA+D;IAC/D,IAAI,CAAC,EAAE,MAAM,CAAC;IACd;;;OAGG;IACH,WAAW,CAAC,EAAE,MAAM,OAAO,CAAC;CAC7B;AAMD,UAAU,OAAO;IACf,+EAA+E;IAC/E;;;;;;;OAOG;IACH,QAAQ,EAAE,CACR,IAAI,EAAE,MAAM,EACZ,cAAc,EAAE,MAAM;IACtB;;;OAGG;IACH,MAAM,EAAE,eAAe;IACvB;;;;;OAKG;IACH,IAAI,EAAE,eAAe,KAClB,IAAI,CAAC;IACV;;;;OAIG;IACH,WAAW,EAAE;QAAE,EAAE,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;IACjD,6EAA6E;IAC7E,QAAQ,EAAE,MAAM,CAAC;IACjB;;;OAGG;IACH,OAAO,CAAC,EAAE,YAAY,GAAG,MAAM,CAAC;IAChC;;;;;OAKG;IACH,WAAW,CAAC,EAAE,MAAM,IAAI,CAAC;CAC1B;AAED,oEAAoE;AACpE,MAAM,WAAW,eAAe;IAC9B,gEAAgE;IAChE,UAAU,EAAE,OAAO,CAAC;CACrB;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,eAAe,CAAC,EAC9B,QAAQ,EACR,WAAW,EACX,QAAQ,EACR,OAAO,EAAE,WAAW,EACpB,WAAW,GACZ,EAAE,OAAO;;IAg5BJ,qEAAqE;;IAErE;;;;;;;OAOG;;IAEH,+DAA+D;;IAE/D;;;;;;;OAOG;;IAIH,0EAA0E;;IAE1E,6DAA6D;;IAE7D,kEAAkE;;IAElE,uEAAuE;;IAEvE,sDAAsD;;;;uCA1GvC,MAAM;;;IAiHrB,qDAAqD;;IAErD,uDAAuD;;IAEvD,0EAA0E;qBAxzB1C,iBAAiB;IA0zBjD;;;OAGG;+BAx0BuC,OAAO;IA00BjD;;;OAGG;0BAvyBE,iBAAiB;EAs0B3B"}
|
|
@@ -1,24 +1,24 @@
|
|
|
1
1
|
import { useVoiceInput as e } from "../voice/useVoiceInput.js";
|
|
2
2
|
import { planSubmitTimer as t, resolveVoiceGraceMs as n } from "../voice/handsFree.js";
|
|
3
3
|
import { speechFeed as r } from "../speech/speechFeed.js";
|
|
4
|
-
import { INITIAL_SESSION as ee, INTERRUPT_MAX_MS as te, NOTHING_HEARD as i, advanceHeardClock as ne, isCapturing as
|
|
5
|
-
import { isTurnSuperseded as
|
|
6
|
-
import { captionChunks as
|
|
7
|
-
import { turnClockMs as
|
|
8
|
-
import { useAssistantSpeech as
|
|
9
|
-
import { useCallback as
|
|
4
|
+
import { INITIAL_SESSION as ee, INTERRUPT_MAX_MS as te, NOTHING_HEARD as i, advanceHeardClock as ne, isCapturing as re, isSubmittable as ie, planListeningHold as ae, planReplyConsumption as oe, planVoiceAnnouncement as se, shouldRecognise as ce, spokenSoFar as a, voiceSessionReducer as le } from "../voice/voiceSession.js";
|
|
5
|
+
import { isTurnSuperseded as o } from "../voice/supersededTurns.js";
|
|
6
|
+
import { captionChunks as ue } from "../voice/speechPlayback.js";
|
|
7
|
+
import { turnClockMs as s } from "../turnTimeline.js";
|
|
8
|
+
import { useAssistantSpeech as de } from "./AssistantSpeechProvider.js";
|
|
9
|
+
import { useCallback as c, useEffect as l, useLayoutEffect as fe, useMemo as pe, useReducer as me, useRef as u, useState as d } from "react";
|
|
10
10
|
//#region src/shared/assistant/ui/useVoiceSession.ts
|
|
11
|
-
var
|
|
12
|
-
function
|
|
13
|
-
let
|
|
14
|
-
|
|
11
|
+
var he = 4e3, ge = 2500, _e = 5e3, ve = 12e3, ye = "data:audio/wav;base64,UklGRiQAAABXQVZFZm10IBAAAAABAAEARKwAAIhYAQACABAAZGF0YQAAAAA=";
|
|
12
|
+
function f({ onSubmit: f, latestReply: p, language: m, graceMs: be, onSupersede: h }) {
|
|
13
|
+
let xe = n(be), g = u(null), [_, v] = me(c((e, t) => le(e, t, g.current), []), ee), y = de(), { setSessionSpeaking: b, setSessionMicOpen: x, speakingMessageId: S, stop: C } = y, w = u(y.toggle), T = y.toggle;
|
|
14
|
+
fe(() => {
|
|
15
15
|
w.current = T;
|
|
16
16
|
}, [T]);
|
|
17
|
-
let E =
|
|
17
|
+
let E = u(null), D = u({}), O = u(i), k = u(null), A = u(!1), j = u(null), [M, N] = d(null), [P, F] = d(!1), [I, L] = d(!1), [R, z] = d(!1), B = u(_);
|
|
18
18
|
B.current = _;
|
|
19
|
-
let V =
|
|
19
|
+
let V = u([]), H = u(null), U = u(!1), W = c(() => {
|
|
20
20
|
V.current = [], H.current = null, U.current = !1;
|
|
21
|
-
}, []), G =
|
|
21
|
+
}, []), G = c(() => {
|
|
22
22
|
for (;;) {
|
|
23
23
|
let e = V.current.shift();
|
|
24
24
|
if (!e) return !1;
|
|
@@ -33,8 +33,8 @@ function ye({ onSubmit: ye, latestReply: p, language: be, graceMs: xe, onSuperse
|
|
|
33
33
|
return !0;
|
|
34
34
|
}
|
|
35
35
|
}
|
|
36
|
-
}, []), K =
|
|
37
|
-
let t =
|
|
36
|
+
}, []), K = u(!1), q = c((e) => {
|
|
37
|
+
let t = ae({
|
|
38
38
|
requested: e,
|
|
39
39
|
held: K.current,
|
|
40
40
|
muted: B.current.muted
|
|
@@ -43,17 +43,17 @@ function ye({ onSubmit: ye, latestReply: p, language: be, graceMs: xe, onSuperse
|
|
|
43
43
|
type: "mute",
|
|
44
44
|
muted: t.mute
|
|
45
45
|
});
|
|
46
|
-
}, []), J =
|
|
47
|
-
let t =
|
|
46
|
+
}, []), J = c((e) => {
|
|
47
|
+
let t = se(B.current);
|
|
48
48
|
t !== "drop" && (H.current?.id === e.id || V.current.some((t) => t.id === e.id) || (V.current.push(e), t === "start" && !U.current && (U.current = !0, v({ type: "announce" }))));
|
|
49
|
-
}, []), Se =
|
|
49
|
+
}, []), Se = c((e) => {
|
|
50
50
|
if (B.current.phase !== "thinking") {
|
|
51
51
|
J(e);
|
|
52
52
|
return;
|
|
53
53
|
}
|
|
54
54
|
V.current.push(e), U.current = !0, v({ type: "answered-locally" });
|
|
55
|
-
}, [J]), Ce =
|
|
56
|
-
Ce.current = p,
|
|
55
|
+
}, [J]), Ce = u(p);
|
|
56
|
+
Ce.current = p, l(() => {
|
|
57
57
|
if (_.phase === "speaking") {
|
|
58
58
|
let e = j.current;
|
|
59
59
|
g.current = e && k.current === e.id && p?.id !== e.id ? e.text : p?.text ?? null;
|
|
@@ -62,40 +62,43 @@ function ye({ onSubmit: ye, latestReply: p, language: be, graceMs: xe, onSuperse
|
|
|
62
62
|
if (g.current === null) return;
|
|
63
63
|
let e = setTimeout(() => {
|
|
64
64
|
g.current = null;
|
|
65
|
-
},
|
|
65
|
+
}, ge);
|
|
66
66
|
return () => clearTimeout(e);
|
|
67
67
|
}, [_.phase, p]);
|
|
68
|
-
let
|
|
68
|
+
let we = u(m);
|
|
69
|
+
we.current = m;
|
|
70
|
+
let Y = c((e, t) => {
|
|
69
71
|
v({
|
|
70
72
|
type: "speech",
|
|
71
73
|
transcript: e,
|
|
72
74
|
final: t,
|
|
73
|
-
at: Date.now()
|
|
75
|
+
at: Date.now(),
|
|
76
|
+
language: we.current
|
|
74
77
|
});
|
|
75
|
-
}, []),
|
|
76
|
-
W(), C(),
|
|
78
|
+
}, []), Te = u(0), Ee = c(() => {
|
|
79
|
+
W(), C(), Te.current = Date.now(), F(!0), v({ type: "interrupt" });
|
|
77
80
|
}, [C, W]), X = e({
|
|
78
|
-
onFinalize:
|
|
79
|
-
language:
|
|
81
|
+
onFinalize: c((e) => Y(e, !0), [Y]),
|
|
82
|
+
language: m
|
|
80
83
|
});
|
|
81
|
-
|
|
84
|
+
l(() => {
|
|
82
85
|
X.interim && Y(X.interim, !1);
|
|
83
|
-
}, [X.interim, Y]),
|
|
84
|
-
E.current && clearTimeout(E.current), L(!1), O.current = ne(O.current, _,
|
|
86
|
+
}, [X.interim, Y]), l(() => {
|
|
87
|
+
E.current && clearTimeout(E.current), L(!1), O.current = ne(O.current, _, s());
|
|
85
88
|
let e = t({
|
|
86
89
|
phase: _.phase,
|
|
87
90
|
muted: _.muted,
|
|
88
|
-
spoken:
|
|
91
|
+
spoken: a(_),
|
|
89
92
|
holding: R,
|
|
90
|
-
graceMs:
|
|
93
|
+
graceMs: xe
|
|
91
94
|
});
|
|
92
95
|
if (!e.arm) return;
|
|
93
|
-
let n = setTimeout(() => L(!0), Math.min(800, e.delayMs)), r =
|
|
96
|
+
let n = setTimeout(() => L(!0), Math.min(800, e.delayMs)), r = s();
|
|
94
97
|
return E.current = setTimeout(() => {
|
|
95
98
|
D.current = {
|
|
96
99
|
speechEnded: O.current.at ?? r,
|
|
97
100
|
graceStarted: r,
|
|
98
|
-
graceEnded:
|
|
101
|
+
graceEnded: s()
|
|
99
102
|
}, v({
|
|
100
103
|
type: "silence",
|
|
101
104
|
at: Date.now()
|
|
@@ -106,34 +109,34 @@ function ye({ onSubmit: ye, latestReply: p, language: be, graceMs: xe, onSuperse
|
|
|
106
109
|
}, [
|
|
107
110
|
_,
|
|
108
111
|
R,
|
|
109
|
-
|
|
110
|
-
]),
|
|
112
|
+
xe
|
|
113
|
+
]), l(() => {
|
|
111
114
|
(_.phase !== "listening" || _.muted) && z(!1);
|
|
112
|
-
}, [_.phase, _.muted]),
|
|
115
|
+
}, [_.phase, _.muted]), l(() => {
|
|
113
116
|
if (!P) return;
|
|
114
|
-
let e = Date.now() -
|
|
117
|
+
let e = Date.now() - Te.current, t = X.isListening ? Math.max(0, 500 - e) : Math.max(0, te - e), n = setTimeout(() => F(!1), t);
|
|
115
118
|
return () => clearTimeout(n);
|
|
116
119
|
}, [P, X.isListening]);
|
|
117
|
-
let
|
|
118
|
-
_.phase === "listening" && (
|
|
120
|
+
let De = u("");
|
|
121
|
+
_.phase === "listening" && (De.current = a(_)), l(() => {
|
|
119
122
|
if (_.phase !== "thinking") return;
|
|
120
123
|
x(!1), W();
|
|
121
|
-
let e =
|
|
122
|
-
e &&
|
|
123
|
-
}, [_.phase]),
|
|
124
|
-
let e =
|
|
124
|
+
let e = De.current.trim();
|
|
125
|
+
e && f(e, Q.current ?? `vs-orphan-${Date.now().toString(36)}`, D.current, { correction: B.current.correcting }), D.current = {}, O.current = i;
|
|
126
|
+
}, [_.phase]), l(() => {
|
|
127
|
+
let e = oe(p?.id, _.phase, k.current, o(p?.id));
|
|
125
128
|
e.claim && (k.current = p?.id ?? null, e.advance && p && v({
|
|
126
129
|
type: "reply",
|
|
127
130
|
text: p.text
|
|
128
131
|
}));
|
|
129
|
-
}, [p, _.phase]),
|
|
132
|
+
}, [p, _.phase]), l(() => {
|
|
130
133
|
if (S === null || _.phase !== "thinking" || k.current === S) return;
|
|
131
|
-
if (
|
|
134
|
+
if (o(S)) {
|
|
132
135
|
C();
|
|
133
136
|
return;
|
|
134
137
|
}
|
|
135
138
|
let e = r.peek(S);
|
|
136
|
-
!e || e.channel !== "voice" || e.voiceSessionId === void 0 || e.voiceSessionId !==
|
|
139
|
+
!e || e.channel !== "voice" || e.voiceSessionId === void 0 || e.voiceSessionId !== Q.current || (k.current = S, j.current = {
|
|
137
140
|
id: S,
|
|
138
141
|
text: e.text
|
|
139
142
|
}, v({
|
|
@@ -144,41 +147,41 @@ function ye({ onSubmit: ye, latestReply: p, language: be, graceMs: xe, onSuperse
|
|
|
144
147
|
S,
|
|
145
148
|
_.phase,
|
|
146
149
|
C
|
|
147
|
-
]),
|
|
150
|
+
]), l(() => {
|
|
148
151
|
let e = S !== null;
|
|
149
152
|
A.current && !e && (H.current = null, (B.current.phase !== "speaking" || !G()) && v({ type: "speech-ended" })), A.current = e;
|
|
150
|
-
}, [S, G]),
|
|
153
|
+
}, [S, G]), l(() => {
|
|
151
154
|
_.phase !== "listening" && N((e) => e === "nothing-heard" ? null : e);
|
|
152
|
-
}, [_.phase]),
|
|
155
|
+
}, [_.phase]), l(() => {
|
|
153
156
|
if (_.phase !== "speaking" || S !== null) return;
|
|
154
157
|
let e = setTimeout(() => {
|
|
155
158
|
A.current || (W(), v({ type: "speech-ended" }));
|
|
156
|
-
},
|
|
159
|
+
}, he);
|
|
157
160
|
return () => clearTimeout(e);
|
|
158
161
|
}, [
|
|
159
162
|
_.phase,
|
|
160
163
|
S,
|
|
161
164
|
W
|
|
162
165
|
]);
|
|
163
|
-
let
|
|
164
|
-
|
|
165
|
-
let
|
|
166
|
-
|
|
166
|
+
let Oe = u(h);
|
|
167
|
+
Oe.current = h;
|
|
168
|
+
let Z = u(0);
|
|
169
|
+
l(() => {
|
|
167
170
|
let e = _.superseded;
|
|
168
|
-
e !==
|
|
171
|
+
e !== Z.current && (Z.current = e, e !== 0 && (W(), C(), Oe.current?.()));
|
|
169
172
|
}, [
|
|
170
173
|
_.superseded,
|
|
171
174
|
W,
|
|
172
175
|
C
|
|
173
|
-
]),
|
|
174
|
-
x(
|
|
176
|
+
]), l(() => {
|
|
177
|
+
x(re(_)), ce(_) ? X.isActive || X.start("auto") : X.isActive && X.stop();
|
|
175
178
|
}, [
|
|
176
179
|
_,
|
|
177
180
|
X,
|
|
178
181
|
x
|
|
179
|
-
]),
|
|
182
|
+
]), l(() => {
|
|
180
183
|
_.phase !== "speaking" || !U.current || (U.current = !1, G() || v({ type: "speech-ended" }));
|
|
181
|
-
}, [_.phase, G]),
|
|
184
|
+
}, [_.phase, G]), l(() => {
|
|
182
185
|
X.error === "not-allowed" || X.error === "audio-capture" ? v({
|
|
183
186
|
type: "fail",
|
|
184
187
|
error: "mic-denied"
|
|
@@ -186,20 +189,20 @@ function ye({ onSubmit: ye, latestReply: p, language: be, graceMs: xe, onSuperse
|
|
|
186
189
|
type: "fail",
|
|
187
190
|
error: "no-speech-support"
|
|
188
191
|
}) : X.error === "network" ? N("network") : X.error === "unknown" && N("recognition-failed");
|
|
189
|
-
}, [X.error]),
|
|
192
|
+
}, [X.error]), l(() => {
|
|
190
193
|
X.error !== null || !X.isListening || N((e) => e === "network" || e === "recognition-failed" ? null : e);
|
|
191
|
-
}, [X.error, X.isListening]),
|
|
192
|
-
if (X.isListening && N((e) => e === "not-capturing" ? null : e), !
|
|
193
|
-
let e = setTimeout(() => N("not-capturing"),
|
|
194
|
+
}, [X.error, X.isListening]), l(() => {
|
|
195
|
+
if (X.isListening && N((e) => e === "not-capturing" ? null : e), !re(_) || X.isListening) return;
|
|
196
|
+
let e = setTimeout(() => N("not-capturing"), _e);
|
|
194
197
|
return () => clearTimeout(e);
|
|
195
|
-
}, [_, X.isListening]),
|
|
196
|
-
if (_.phase !== "listening" || _.muted || !X.isListening ||
|
|
197
|
-
let e = setTimeout(() => N("nothing-heard"),
|
|
198
|
+
}, [_, X.isListening]), l(() => {
|
|
199
|
+
if (_.phase !== "listening" || _.muted || !X.isListening || a(_) !== "") return;
|
|
200
|
+
let e = setTimeout(() => N("nothing-heard"), ve);
|
|
198
201
|
return () => clearTimeout(e);
|
|
199
|
-
}, [_, X.isListening]),
|
|
200
|
-
|
|
202
|
+
}, [_, X.isListening]), l(() => {
|
|
203
|
+
a(_) !== "" && N(null);
|
|
201
204
|
}, [_]);
|
|
202
|
-
let
|
|
205
|
+
let Q = u(null), ke = c(() => {
|
|
203
206
|
if (F(!1), L(!1), z(!1), W(), K.current = !1, !X.isSupported) {
|
|
204
207
|
v({
|
|
205
208
|
type: "fail",
|
|
@@ -223,30 +226,30 @@ function ye({ onSubmit: ye, latestReply: p, language: be, graceMs: xe, onSuperse
|
|
|
223
226
|
} catch {}
|
|
224
227
|
try {
|
|
225
228
|
if (typeof window < "u" && typeof window.Audio == "function") {
|
|
226
|
-
let e = new window.Audio(
|
|
229
|
+
let e = new window.Audio(ye);
|
|
227
230
|
e.volume = 0, e.play().catch(() => {});
|
|
228
231
|
}
|
|
229
232
|
} catch {}
|
|
230
|
-
b(!0), N(null), k.current = Ce.current?.id ?? null, j.current = null,
|
|
233
|
+
b(!0), N(null), k.current = Ce.current?.id ?? null, j.current = null, Q.current = `vs-${Date.now().toString(36)}-${Math.random().toString(36).slice(2, 8)}`, v({ type: "start" });
|
|
231
234
|
}, [
|
|
232
235
|
X.isSupported,
|
|
233
236
|
y.isBlocked,
|
|
234
237
|
b,
|
|
235
238
|
W
|
|
236
|
-
]),
|
|
237
|
-
F(!1), L(!1), z(!1), W(), K.current = !1,
|
|
239
|
+
]), Ae = c(() => {
|
|
240
|
+
F(!1), L(!1), z(!1), W(), K.current = !1, Q.current = null, v({ type: "end" }), C(), b(!1);
|
|
238
241
|
}, [
|
|
239
242
|
C,
|
|
240
243
|
b,
|
|
241
244
|
W
|
|
242
|
-
]),
|
|
245
|
+
]), je = c((e) => Q.current === e, []), Me = c(() => {
|
|
243
246
|
let e = B.current;
|
|
244
247
|
e.phase !== "listening" || e.muted || z(!0);
|
|
245
|
-
}, []),
|
|
248
|
+
}, []), Ne = c(() => {
|
|
246
249
|
z(!1);
|
|
247
250
|
let e = B.current;
|
|
248
|
-
if (e.phase !== "listening" || e.muted || !
|
|
249
|
-
let t =
|
|
251
|
+
if (e.phase !== "listening" || e.muted || !ie(a(e))) return;
|
|
252
|
+
let t = s();
|
|
250
253
|
D.current = {
|
|
251
254
|
speechEnded: O.current.at ?? t,
|
|
252
255
|
graceStarted: t,
|
|
@@ -255,17 +258,17 @@ function ye({ onSubmit: ye, latestReply: p, language: be, graceMs: xe, onSuperse
|
|
|
255
258
|
type: "silence",
|
|
256
259
|
at: Date.now()
|
|
257
260
|
});
|
|
258
|
-
}, []),
|
|
261
|
+
}, []), Pe = c(() => {
|
|
259
262
|
v({
|
|
260
263
|
type: "mute",
|
|
261
264
|
muted: !B.current.muted
|
|
262
265
|
});
|
|
263
266
|
}, []);
|
|
264
|
-
|
|
267
|
+
l(() => () => {
|
|
265
268
|
b(!1), x(!1);
|
|
266
269
|
}, [b, x]);
|
|
267
|
-
let $ =
|
|
268
|
-
return
|
|
270
|
+
let $ = ue(y.spokenChunks, _.phase, S);
|
|
271
|
+
return pe(() => ({
|
|
269
272
|
session: _,
|
|
270
273
|
notice: M,
|
|
271
274
|
spokenChunks: $,
|
|
@@ -276,13 +279,13 @@ function ye({ onSubmit: ye, latestReply: p, language: be, graceMs: xe, onSuperse
|
|
|
276
279
|
holding: R,
|
|
277
280
|
correcting: _.correcting,
|
|
278
281
|
available: X.isSupported && !y.isBlocked,
|
|
279
|
-
start:
|
|
280
|
-
end:
|
|
281
|
-
isCurrentSession:
|
|
282
|
-
toggleMute:
|
|
283
|
-
interrupt:
|
|
284
|
-
letMeFinish:
|
|
285
|
-
imDone:
|
|
282
|
+
start: ke,
|
|
283
|
+
end: Ae,
|
|
284
|
+
isCurrentSession: je,
|
|
285
|
+
toggleMute: Pe,
|
|
286
|
+
interrupt: Ee,
|
|
287
|
+
letMeFinish: Me,
|
|
288
|
+
imDone: Ne,
|
|
286
289
|
announce: J,
|
|
287
290
|
holdListening: q,
|
|
288
291
|
answerLocally: Se
|
|
@@ -296,17 +299,17 @@ function ye({ onSubmit: ye, latestReply: p, language: be, graceMs: xe, onSuperse
|
|
|
296
299
|
X.isSupported,
|
|
297
300
|
y.isBlocked,
|
|
298
301
|
$,
|
|
299
|
-
Q,
|
|
300
302
|
ke,
|
|
301
303
|
Ae,
|
|
302
|
-
Ne,
|
|
303
|
-
Te,
|
|
304
304
|
je,
|
|
305
|
+
Pe,
|
|
306
|
+
Ee,
|
|
305
307
|
Me,
|
|
308
|
+
Ne,
|
|
306
309
|
J,
|
|
307
310
|
q,
|
|
308
311
|
Se
|
|
309
312
|
]);
|
|
310
313
|
}
|
|
311
314
|
//#endregion
|
|
312
|
-
export {
|
|
315
|
+
export { f as useVoiceSession };
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Bare affirmations, per speaking language (BOFF-8613, F1b).
|
|
3
|
+
*
|
|
4
|
+
* `classifyWriteReply` is an ENGLISH classifier: for any other locale it
|
|
5
|
+
* answers "other". `planThinkingSpeech` used to call it with a hard-coded
|
|
6
|
+
* "en", so a Hindi "हाँ", a Tamil "சரி", a Spanish "vale", an Arabic "نعم" or a
|
|
7
|
+
* Chinese "好的" said while an answer was being prepared was not a bare
|
|
8
|
+
* affirmation at all: it aborted the turn and re-sent it as a correction.
|
|
9
|
+
*
|
|
10
|
+
* Nothing here approves or commits anything. This file only answers "is this
|
|
11
|
+
* utterance nothing but a yes?", so that `planThinkingSpeech` can leave the
|
|
12
|
+
* turn alone. The binder, and the card's button, stay the only way a change is
|
|
13
|
+
* confirmed.
|
|
14
|
+
*
|
|
15
|
+
* Pure data in, answer out: no DOM, no timers.
|
|
16
|
+
*/
|
|
17
|
+
/** The languages the assistant is offered in (`languages.ts`). */
|
|
18
|
+
export type AffirmationLanguage = "en" | "hi" | "ta" | "es" | "ar" | "zh";
|
|
19
|
+
/**
|
|
20
|
+
* "hi-IN", "ta_IN", "zh-Hant-TW" -> the language this module has a lexicon
|
|
21
|
+
* for. Anything unknown (or absent) is English: that is what the assistant
|
|
22
|
+
* classified with before this module existed, so a new locale degrades to the
|
|
23
|
+
* old behaviour and never to a looser one.
|
|
24
|
+
*/
|
|
25
|
+
export declare function resolveAffirmationLanguage(language: string | null | undefined): AffirmationLanguage;
|
|
26
|
+
/**
|
|
27
|
+
* Is this utterance NOTHING but a yes, in the language being spoken?
|
|
28
|
+
*
|
|
29
|
+
* English is the 5a classifier itself, so "yes please thanks" and "ok go
|
|
30
|
+
* ahead" mean here exactly what they mean to the binder. The other languages
|
|
31
|
+
* use the lexicons above. A yes WITH a change ("yes but make it 9", "好的但是
|
|
32
|
+
* 改成九点") is not bare: it is a correction.
|
|
33
|
+
*/
|
|
34
|
+
export declare function isBareAffirmation(text: string, language: string | null | undefined): boolean;
|
|
35
|
+
/**
|
|
36
|
+
* Does the utterance hold anything that is not a yes (or part of one)?
|
|
37
|
+
*
|
|
38
|
+
* "ok go" is made only of the tokens of "ok" and "go ahead": it is the START
|
|
39
|
+
* of a yes, and nothing yet to correct. "ok go ahead and plant ragi" has
|
|
40
|
+
* content. `interim` lets the last token be a prefix of a yes token, because a
|
|
41
|
+
* live guess can end mid-word ("ok go ahe").
|
|
42
|
+
*/
|
|
43
|
+
export declare function hasContentBeyondAffirmation(text: string, language: string | null | undefined, interim?: boolean): boolean;
|
|
44
|
+
//# sourceMappingURL=affirmations.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"affirmations.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/voice/affirmations.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAIH,kEAAkE;AAClE,MAAM,MAAM,mBAAmB,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;AAiL1E;;;;;GAKG;AACH,wBAAgB,0BAA0B,CAAC,QAAQ,EAAE,MAAM,GAAG,IAAI,GAAG,SAAS,GAAG,mBAAmB,CAYnG;AAoFD;;;;;;;GAOG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,IAAI,GAAG,SAAS,GAAG,OAAO,CAM5F;AAED;;;;;;;GAOG;AACH,wBAAgB,2BAA2B,CACzC,IAAI,EAAE,MAAM,EACZ,QAAQ,EAAE,MAAM,GAAG,IAAI,GAAG,SAAS,EACnC,OAAO,UAAQ,GACd,OAAO,CAcT"}
|