@burdenoff/fe-libs 2026.1007.4 → 2026.1007.6

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.
Files changed (166) hide show
  1. package/dist/chrome/AutoBreadcrumbs.d.ts.map +1 -1
  2. package/dist/chrome/AutoBreadcrumbs.js +65 -76
  3. package/dist/chrome/Breadcrumb.d.ts.map +1 -1
  4. package/dist/chrome/Breadcrumbs.d.ts.map +1 -1
  5. package/dist/chrome/Breadcrumbs.js +47 -46
  6. package/dist/chrome/ContextSwitcher.js +86 -86
  7. package/dist/chrome/HeaderBar.d.ts.map +1 -1
  8. package/dist/chrome/HeaderBar.js +111 -107
  9. package/dist/chrome/HeaderThemeSwitcher.d.ts.map +1 -1
  10. package/dist/chrome/HeaderThemeSwitcher.js +46 -45
  11. package/dist/chrome/LanguageSwitcher.js +4 -4
  12. package/dist/chrome/MobileTabBar.js +4 -4
  13. package/dist/chrome/PageHeader.d.ts.map +1 -1
  14. package/dist/chrome/PageHeader.js +32 -30
  15. package/dist/chrome/PersonaSurfaceControls.js +8 -8
  16. package/dist/chrome/ProductSideNav.js +6 -6
  17. package/dist/chrome/ProfileSwitcher.d.ts.map +1 -1
  18. package/dist/chrome/ProfileSwitcher.js +89 -88
  19. package/dist/chrome/SideNavigation.js +4 -4
  20. package/dist/chrome/Tabs.d.ts.map +1 -1
  21. package/dist/chrome/Tabs.js +30 -29
  22. package/dist/chrome/breadcrumbLabel.d.ts +10 -0
  23. package/dist/chrome/breadcrumbLabel.d.ts.map +1 -0
  24. package/dist/chrome/breadcrumbLabel.js +31 -0
  25. package/dist/chrome/contextSwitcher/TriggerButton.d.ts.map +1 -1
  26. package/dist/chrome/contextSwitcher/TriggerButton.js +40 -36
  27. package/dist/chrome/notificationCenter/BellButton.d.ts.map +1 -1
  28. package/dist/chrome/notificationCenter/BellButton.js +29 -25
  29. package/dist/chrome/shellLabelManifest.d.ts +27 -0
  30. package/dist/chrome/shellLabelManifest.d.ts.map +1 -0
  31. package/dist/chrome/sideNavigation/SidebarHeader.d.ts.map +1 -1
  32. package/dist/chrome/sideNavigation/SidebarHeader.js +23 -22
  33. package/dist/shared/assistant/api.d.ts +11 -0
  34. package/dist/shared/assistant/api.d.ts.map +1 -1
  35. package/dist/shared/assistant/api.js +6 -2
  36. package/dist/shared/assistant/appControls/languageReply.d.ts +6 -1
  37. package/dist/shared/assistant/appControls/languageReply.d.ts.map +1 -1
  38. package/dist/shared/assistant/conversation.d.ts +14 -0
  39. package/dist/shared/assistant/conversation.d.ts.map +1 -1
  40. package/dist/shared/assistant/createSandboxAssistantTransport.d.ts +8 -1
  41. package/dist/shared/assistant/createSandboxAssistantTransport.d.ts.map +1 -1
  42. package/dist/shared/assistant/createSandboxAssistantTransport.js +70 -51
  43. package/dist/shared/assistant/history/historyMapping.d.ts.map +1 -1
  44. package/dist/shared/assistant/history/historyMapping.js +19 -12
  45. package/dist/shared/assistant/i18nManifest.d.ts +26 -5
  46. package/dist/shared/assistant/i18nManifest.d.ts.map +1 -1
  47. package/dist/shared/assistant/i18nManifest.js +36 -22
  48. package/dist/shared/assistant/index.d.ts +7 -0
  49. package/dist/shared/assistant/index.d.ts.map +1 -1
  50. package/dist/shared/assistant/localUiCommandCopy.d.ts +23 -0
  51. package/dist/shared/assistant/localUiCommandCopy.d.ts.map +1 -1
  52. package/dist/shared/assistant/localUiCommandCopy.js +60 -23
  53. package/dist/shared/assistant/localUiCommands.d.ts +29 -0
  54. package/dist/shared/assistant/localUiCommands.d.ts.map +1 -1
  55. package/dist/shared/assistant/localUiCommands.js +18 -7
  56. package/dist/shared/assistant/productCopy.d.ts +78 -0
  57. package/dist/shared/assistant/productCopy.d.ts.map +1 -0
  58. package/dist/shared/assistant/productCopy.js +45 -0
  59. package/dist/shared/assistant/types.d.ts +19 -8
  60. package/dist/shared/assistant/types.d.ts.map +1 -1
  61. package/dist/shared/assistant/ui/AssistantChatArea.d.ts.map +1 -1
  62. package/dist/shared/assistant/ui/AssistantChatArea.js +1479 -1140
  63. package/dist/shared/assistant/ui/AssistantEmptyState.d.ts.map +1 -1
  64. package/dist/shared/assistant/ui/AssistantEmptyState.js +30 -22
  65. package/dist/shared/assistant/ui/AssistantHeader.d.ts.map +1 -1
  66. package/dist/shared/assistant/ui/AssistantHeader.js +46 -45
  67. package/dist/shared/assistant/ui/AssistantMarkdownRenderer.d.ts +18 -3
  68. package/dist/shared/assistant/ui/AssistantMarkdownRenderer.d.ts.map +1 -1
  69. package/dist/shared/assistant/ui/AssistantMarkdownRenderer.js +1 -1
  70. package/dist/shared/assistant/ui/AssistantMessageItem.d.ts +5 -0
  71. package/dist/shared/assistant/ui/AssistantMessageItem.d.ts.map +1 -1
  72. package/dist/shared/assistant/ui/AssistantMessageItem.js +89 -84
  73. package/dist/shared/assistant/ui/AssistantMessageList.d.ts +5 -0
  74. package/dist/shared/assistant/ui/AssistantMessageList.d.ts.map +1 -1
  75. package/dist/shared/assistant/ui/AssistantMessageList.js +26 -25
  76. package/dist/shared/assistant/ui/AssistantUiOfferLink.d.ts +45 -0
  77. package/dist/shared/assistant/ui/AssistantUiOfferLink.d.ts.map +1 -0
  78. package/dist/shared/assistant/ui/AssistantUiOfferLink.js +56 -0
  79. package/dist/shared/assistant/ui/assistantOverlayState.d.ts +9 -0
  80. package/dist/shared/assistant/ui/assistantOverlayState.d.ts.map +1 -1
  81. package/dist/shared/assistant/ui/assistantOverlayState.js +37 -28
  82. package/dist/shared/assistant/ui/composer/AssistantConnectSourceItem.d.ts.map +1 -1
  83. package/dist/shared/assistant/ui/composer/AssistantConnectSourceItem.js +1 -1
  84. package/dist/shared/assistant/ui/voice/AssistantVoiceSession.d.ts +5 -0
  85. package/dist/shared/assistant/ui/voice/AssistantVoiceSession.d.ts.map +1 -1
  86. package/dist/shared/assistant/ui/voice/AssistantVoiceSession.js +12 -11
  87. package/dist/shared/assistant/ui/voice/VoiceConversationView.d.ts +6 -1
  88. package/dist/shared/assistant/ui/voice/VoiceConversationView.d.ts.map +1 -1
  89. package/dist/shared/assistant/ui/voice/VoiceConversationView.js +7 -7
  90. package/dist/shared/assistant/ui/voice/VoiceTranscriptDrawer.d.ts +6 -1
  91. package/dist/shared/assistant/ui/voice/VoiceTranscriptDrawer.d.ts.map +1 -1
  92. package/dist/shared/assistant/ui/voice/VoiceTranscriptDrawer.js +15 -12
  93. package/dist/shared/assistant/uiActions/actOnResolve.d.ts +108 -0
  94. package/dist/shared/assistant/uiActions/actOnResolve.d.ts.map +1 -0
  95. package/dist/shared/assistant/uiActions/actOnResolve.js +51 -0
  96. package/dist/shared/assistant/uiActions/linkContext.d.ts +29 -0
  97. package/dist/shared/assistant/uiActions/linkContext.d.ts.map +1 -1
  98. package/dist/shared/assistant/uiActions/linkContext.js +37 -10
  99. package/dist/shared/assistant/uiActions/navIntent.d.ts +58 -0
  100. package/dist/shared/assistant/uiActions/navIntent.d.ts.map +1 -0
  101. package/dist/shared/assistant/uiActions/navIntent.js +79 -0
  102. package/dist/shared/assistant/uiActions/navigateAction.d.ts +6 -1
  103. package/dist/shared/assistant/uiActions/navigateAction.d.ts.map +1 -1
  104. package/dist/shared/assistant/uiActions/navigateAction.js +18 -14
  105. package/dist/shared/assistant/uiActions/navigationOutcome.d.ts +16 -2
  106. package/dist/shared/assistant/uiActions/navigationOutcome.d.ts.map +1 -1
  107. package/dist/shared/assistant/uiActions/navigationOutcome.js +6 -2
  108. package/dist/shared/assistant/uiActions/offerYesOnSurface.d.ts +39 -0
  109. package/dist/shared/assistant/uiActions/offerYesOnSurface.d.ts.map +1 -0
  110. package/dist/shared/assistant/uiActions/offerYesOnSurface.js +34 -0
  111. package/dist/shared/assistant/uiActions/uiCatalogue.d.ts +14 -0
  112. package/dist/shared/assistant/uiActions/uiCatalogue.d.ts.map +1 -1
  113. package/dist/shared/assistant/uiActions/uiCatalogue.js +23 -3
  114. package/dist/shared/assistant/uiActions/uiOffers.d.ts +249 -0
  115. package/dist/shared/assistant/uiActions/uiOffers.d.ts.map +1 -0
  116. package/dist/shared/assistant/uiActions/uiOffers.js +195 -0
  117. package/dist/shared/assistant/writeProposals.d.ts +6 -0
  118. package/dist/shared/assistant/writeProposals.d.ts.map +1 -1
  119. package/dist/shared/assistant/writeReplyBinder.d.ts +40 -0
  120. package/dist/shared/assistant/writeReplyBinder.d.ts.map +1 -1
  121. package/dist/shared/assistant/writeReplyBinder.js +100 -83
  122. package/dist/shared/assistant/writeReplySend.d.ts +14 -0
  123. package/dist/shared/assistant/writeReplySend.d.ts.map +1 -1
  124. package/dist/shared/assistant/writeReplySend.js +32 -29
  125. package/dist/shared/components/ContextConversationWidget.js +1 -1
  126. package/dist/shared/events/sinks/RybbitSink.d.ts.map +1 -1
  127. package/dist/shared/events/sinks/RybbitSink.js +66 -69
  128. package/dist/shared/hooks/index.d.ts +2 -0
  129. package/dist/shared/hooks/index.d.ts.map +1 -1
  130. package/dist/shared/navigation/unsavedChanges.d.ts +83 -0
  131. package/dist/shared/navigation/unsavedChanges.d.ts.map +1 -0
  132. package/dist/shared/navigation/unsavedChanges.js +46 -0
  133. package/dist/shared/providers/AppShellProvider.d.ts +17 -0
  134. package/dist/shared/providers/AppShellProvider.d.ts.map +1 -1
  135. package/dist/shared/providers/AppShellProvider.js +188 -180
  136. package/dist/shared/providers/shell/I18nProvider.d.ts +92 -4
  137. package/dist/shared/providers/shell/I18nProvider.d.ts.map +1 -1
  138. package/dist/shared/providers/shell/I18nProvider.js +187 -79
  139. package/dist/shared/providers/shell/ProfileI18nBridge.d.ts +18 -2
  140. package/dist/shared/providers/shell/ProfileI18nBridge.d.ts.map +1 -1
  141. package/dist/shared/providers/shell/ProfileI18nBridge.js +55 -41
  142. package/dist/shared/providers/shell/directionMode.d.ts +25 -0
  143. package/dist/shared/providers/shell/directionMode.d.ts.map +1 -0
  144. package/dist/shared/providers/shell/directionMode.js +34 -0
  145. package/dist/shared/providers/shell/index.d.ts +4 -2
  146. package/dist/shared/providers/shell/index.d.ts.map +1 -1
  147. package/dist/shared/providers/shell/translationLayers.d.ts +30 -0
  148. package/dist/shared/providers/shell/translationLayers.d.ts.map +1 -0
  149. package/dist/shared/providers/shell/translationLayers.js +35 -0
  150. package/dist/shared/providers/shell/translationStore.d.ts +55 -0
  151. package/dist/shared/providers/shell/translationStore.d.ts.map +1 -0
  152. package/dist/shared/providers/shell/translationStore.js +100 -0
  153. package/dist/shared/providers/shell/useShellLabel.d.ts +13 -1
  154. package/dist/shared/providers/shell/useShellLabel.d.ts.map +1 -1
  155. package/dist/shared/providers/shell/useShellLabel.js +10 -9
  156. package/dist/shared-assistant.js +244 -237
  157. package/dist/shared-hooks.js +10 -9
  158. package/dist/shared-providers-shell.js +20 -19
  159. package/dist/shared.js +20 -19
  160. package/dist/ui/boff-ui2.d.ts.map +1 -1
  161. package/dist/ui/cta-overflow-menu.d.ts.map +1 -1
  162. package/dist/ui/cta-overflow-menu.js +20 -18
  163. package/dist/ui/guidance.d.ts +1 -1
  164. package/dist/ui/guidance.d.ts.map +1 -1
  165. package/dist/ui/guidance.js +53 -52
  166. package/package.json +3 -2
@@ -48,6 +48,11 @@ interface Props {
48
48
  * Approve (and no "go ahead") can come from it. Absent, nothing is hidden.
49
49
  */
50
50
  hidesLegacyWriteCard?: (message: Message) => boolean;
51
+ /**
52
+ * ★ BOFF-8060 (N3): a reply's "Open {page}" offer link, drawn under its
53
+ * text. Absent, none are drawn.
54
+ */
55
+ renderUiOffers?: (message: Message) => ReactNode;
51
56
  }
52
57
  /** At most one auto-scroll per this long while a reply is streaming in live. */
53
58
  export declare const LIVE_SCROLL_GAP_MS = 250;
@@ -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;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"}
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;IACrD;;;OAGG;IACH,cAAc,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,KAAK,SAAS,CAAC;CAClD;AAED,gFAAgF;AAChF,eAAO,MAAM,kBAAkB,MAAM,CAAC;AAEtC,eAAO,MAAM,oBAAoB,EAAE,EAAE,CAAC,KAAK,CA2J1C,CAAC"}
@@ -6,61 +6,62 @@ import { useLiveOverlay as o } from "../liveOverlay.js";
6
6
  import { useEffect as s, useRef as c } from "react";
7
7
  import { jsx as l, jsxs as u } from "react/jsx-runtime";
8
8
  //#region src/shared/assistant/ui/AssistantMessageList.tsx
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 = (() => {
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, renderUiOffers: S }) => {
10
+ let C = e(), w = (() => {
11
11
  for (let e = h.length - 1; e >= 0; --e) if (h[e].role === "assistant") return h[e].id;
12
12
  return null;
13
- })(), w = n(h), T = r(h), E = t(h), D = c(null), O = c(null);
13
+ })(), T = n(h), E = r(h), D = t(h), O = c(null), k = c(null);
14
14
  s(() => {
15
- let e = O.current;
15
+ let e = k.current;
16
16
  if (e && e.scrollHeight - e.scrollTop - e.clientHeight < 100) {
17
17
  let e = i();
18
- D.current?.scrollIntoView({ behavior: e ? "auto" : "smooth" });
18
+ O.current?.scrollIntoView({ behavior: e ? "auto" : "smooth" });
19
19
  }
20
20
  }, [h, _]);
21
- let k = o((e) => e.byMessageId), A = _ === null ? null : k[_]?.content ?? null, j = c(0), M = c(null);
21
+ let A = o((e) => e.byMessageId), j = _ === null ? null : A[_]?.content ?? null, M = c(0), N = c(null);
22
22
  return s(() => {
23
- if (A === null) return;
23
+ if (j === null) return;
24
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);
25
+ N.current = null, M.current = Date.now();
26
+ let e = k.current;
27
+ e && e.scrollHeight - e.scrollTop - e.clientHeight < 100 && O.current?.scrollIntoView({ behavior: "auto" });
28
+ }, t = M.current + 250 - Date.now();
29
+ t <= 0 ? e() : N.current === null && (N.current = setTimeout(e, t));
30
+ }, [j]), s(() => () => {
31
+ N.current !== null && clearTimeout(N.current);
32
32
  }, []), s(() => {
33
- D.current?.scrollIntoView({ behavior: "instant" });
33
+ O.current?.scrollIntoView({ behavior: "instant" });
34
34
  }, []), /* @__PURE__ */ u("div", {
35
- ref: O,
35
+ ref: k,
36
36
  className: "scrollbar-slim flex-1 space-y-4 overflow-y-auto p-3",
37
37
  role: "log",
38
38
  "aria-live": "polite",
39
39
  "aria-relevant": "additions",
40
40
  "aria-busy": _ !== null,
41
- "aria-label": S("messageList.ariaLabel", "Conversation messages"),
41
+ "aria-label": C("messageList.ariaLabel", "Conversation messages"),
42
42
  children: [h.map((e) => {
43
- let t = w.has(e.id), n = !t && (e.id === p || e.id === _);
43
+ let t = T.has(e.id), n = !t && (e.id === p || e.id === _);
44
44
  return /* @__PURE__ */ l(a, {
45
45
  onApprovePendingWrite: n ? d : void 0,
46
46
  approvingWriteRef: f,
47
47
  pendingWriteApproved: t,
48
- pendingWriteGoAheadSent: T.has(e.id),
48
+ pendingWriteGoAheadSent: E.has(e.id),
49
49
  pendingWriteExpired: !t && !n,
50
- message: e.id === _ && A !== null ? {
50
+ message: e.id === _ && j !== null ? {
51
51
  ...e,
52
- content: A
52
+ content: j
53
53
  } : e,
54
54
  processing: g,
55
55
  isStreaming: e.id === _,
56
56
  isFailed: e.id === v,
57
57
  isLastAssistant: e.id === m,
58
- isNewestAssistant: e.id === C,
59
- onRetry: E.has(e.id) ? void 0 : y,
58
+ isNewestAssistant: e.id === w,
59
+ onRetry: D.has(e.id) ? void 0 : y,
60
60
  legacyWriteCardHidden: x?.(e) ?? !1,
61
- writeProposals: b?.(e)
61
+ writeProposals: b?.(e),
62
+ uiOffers: S?.(e)
62
63
  }, e.id);
63
- }), /* @__PURE__ */ l("div", { ref: D })]
64
+ }), /* @__PURE__ */ l("div", { ref: O })]
64
65
  });
65
66
  };
66
67
  //#endregion
@@ -0,0 +1,45 @@
1
+ import { FC, MouseEvent } from 'react';
2
+ /**
3
+ * ★ BOFF-8060 (N3, design §4): the page the model offered, as a link under the
4
+ * reply — never a confirm button.
5
+ *
6
+ * - A real `<a href>` to the REGISTRY path: middle-click and Ctrl/Cmd/Shift/Alt
7
+ * click open it the browser's own way, at sidebar parity, and are not
8
+ * intercepted (nor recorded).
9
+ * - A plain click is handed to the panel (`onOpen`), which re-validates the
10
+ * offer against the live registry and navigates through its registered
11
+ * handler (`runNavigation`). This component never navigates by itself.
12
+ * - The text is "Open {page}" with the REGISTRY label, never the model's words.
13
+ * - Announced once through a polite live region; focus is never moved, and
14
+ * nothing animates.
15
+ * - Semantic tokens only (rule 7); logical padding; the arrow mirrors in RTL.
16
+ */
17
+ export interface AssistantUiOfferLinkItem {
18
+ offerId: string;
19
+ /** The registry label. */
20
+ label: string;
21
+ /** The registry path (`navTargetPath`). */
22
+ path: string;
23
+ }
24
+ export interface AssistantUiOfferLinkProps extends AssistantUiOfferLinkItem {
25
+ /** A plain, unmodified primary click, with the label the link showed. */
26
+ onOpen: (offerId: string, label: string) => void;
27
+ }
28
+ /** A click the browser should handle itself: new tab, new window, download. */
29
+ export declare function isModifiedClick(event: Pick<MouseEvent, "button" | "metaKey" | "ctrlKey" | "shiftKey" | "altKey">): boolean;
30
+ export declare const UI_OFFER_LINK_CLASS = "inline-flex items-center gap-2 min-h-11 ps-3 pe-3 rounded-md bg-bg-elevated text-text-link border border-border-default focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-border-strong";
31
+ export declare const AssistantUiOfferLink: FC<AssistantUiOfferLinkProps>;
32
+ export interface AssistantUiOfferLinksProps {
33
+ offers: readonly AssistantUiOfferLinkItem[];
34
+ /** `read`: "…or “yes”" may be said; `link`: tap or "take me there" only. */
35
+ hint: "read" | "link";
36
+ onOpen: (offerId: string, label: string) => void;
37
+ }
38
+ /**
39
+ * The reply's offers and the hint under them. Renders nothing for no offer.
40
+ *
41
+ * The live region starts empty and is filled once after mount, so a screen
42
+ * reader announces it once; it is never changed again for the same offers.
43
+ */
44
+ export declare const AssistantUiOfferLinks: FC<AssistantUiOfferLinksProps>;
45
+ //# sourceMappingURL=AssistantUiOfferLink.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"AssistantUiOfferLink.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/AssistantUiOfferLink.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAuB,KAAK,EAAE,EAAE,KAAK,UAAU,EAAE,MAAM,OAAO,CAAC;AAUtE;;;;;;;;;;;;;;GAcG;AACH,MAAM,WAAW,wBAAwB;IACvC,OAAO,EAAE,MAAM,CAAC;IAChB,0BAA0B;IAC1B,KAAK,EAAE,MAAM,CAAC;IACd,2CAA2C;IAC3C,IAAI,EAAE,MAAM,CAAC;CACd;AAED,MAAM,WAAW,yBAA0B,SAAQ,wBAAwB;IACzE,yEAAyE;IACzE,MAAM,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;CAClD;AAED,+EAA+E;AAC/E,wBAAgB,eAAe,CAC7B,KAAK,EAAE,IAAI,CACT,UAAU,EACV,QAAQ,GAAG,SAAS,GAAG,SAAS,GAAG,UAAU,GAAG,QAAQ,CACzD,GACA,OAAO,CAQT;AAED,eAAO,MAAM,mBAAmB,6MAC4K,CAAC;AAE7M,eAAO,MAAM,oBAAoB,EAAE,EAAE,CAAC,yBAAyB,CAuB9D,CAAC;AAEF,MAAM,WAAW,0BAA0B;IACzC,MAAM,EAAE,SAAS,wBAAwB,EAAE,CAAC;IAC5C,4EAA4E;IAC5E,IAAI,EAAE,MAAM,GAAG,MAAM,CAAC;IACtB,MAAM,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;CAClD;AAED;;;;;GAKG;AACH,eAAO,MAAM,qBAAqB,EAAE,EAAE,CAAC,0BAA0B,CA+ChE,CAAC"}
@@ -0,0 +1,56 @@
1
+ import { useAssistantTr as e } from "../i18n.js";
2
+ import { offerAnnounceText as t, offerHintText as n, offerOpenText as r } from "../localUiCommandCopy.js";
3
+ import { useEffect as i, useState as a } from "react";
4
+ import { ArrowRight as o } from "lucide-react";
5
+ import { jsx as s, jsxs as c } from "react/jsx-runtime";
6
+ //#region src/shared/assistant/ui/AssistantUiOfferLink.tsx
7
+ function l(e) {
8
+ return e.button !== 0 || e.metaKey || e.ctrlKey || e.shiftKey || e.altKey;
9
+ }
10
+ var u = "inline-flex items-center gap-2 min-h-11 ps-3 pe-3 rounded-md bg-bg-elevated text-text-link border border-border-default focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-border-strong", d = ({ offerId: t, label: n, path: i, onOpen: a }) => /* @__PURE__ */ c("a", {
11
+ href: i,
12
+ className: u,
13
+ "data-testid": "assistant-ui-offer-link",
14
+ "data-offer-id": t,
15
+ onClick: (e) => {
16
+ e.defaultPrevented || l(e) || (e.preventDefault(), a(t, n));
17
+ },
18
+ children: [/* @__PURE__ */ s("span", { children: r(e(), n) }), /* @__PURE__ */ s(o, {
19
+ className: "size-4 rtl:rotate-180",
20
+ "aria-hidden": "true"
21
+ })]
22
+ }), f = ({ offers: r, hint: o, onOpen: l }) => {
23
+ let u = e(), f = r[0], p = f ? t(u, f.label) : "", m = f?.offerId ?? "", [h, g] = a({
24
+ key: "",
25
+ text: ""
26
+ });
27
+ return i(() => {
28
+ m && g((e) => e.key === m ? e : {
29
+ key: m,
30
+ text: p
31
+ });
32
+ }, [m, p]), f ? /* @__PURE__ */ c("div", {
33
+ className: "mt-2 flex flex-col items-start gap-1",
34
+ "data-testid": "assistant-ui-offers",
35
+ children: [
36
+ r.map((e) => /* @__PURE__ */ s(d, {
37
+ ...e,
38
+ onOpen: l
39
+ }, e.offerId)),
40
+ /* @__PURE__ */ s("p", {
41
+ className: "text-xs text-text-secondary",
42
+ "data-testid": "assistant-ui-offer-hint",
43
+ children: n(u, o)
44
+ }),
45
+ /* @__PURE__ */ s("span", {
46
+ className: "sr-only",
47
+ role: "status",
48
+ "aria-live": "polite",
49
+ "data-testid": "assistant-ui-offer-announce",
50
+ children: h.key === m ? h.text : ""
51
+ })
52
+ ]
53
+ }) : null;
54
+ };
55
+ //#endregion
56
+ export { d as AssistantUiOfferLink, f as AssistantUiOfferLinks, u as UI_OFFER_LINK_CLASS, l as isModifiedClick };
@@ -235,6 +235,15 @@ export interface AssistantNavigateOptions {
235
235
  * for renders beneath the sheet, so it steps aside — but closing unmounts the
236
236
  * panel, and collapsing is a class swap on the same node. On desktop the panel
237
237
  * sits beside the page and nothing moves.
238
+ *
239
+ * ★★ BOFF-8060 (N4, the leave-page guard): a navigation the ASSISTANT started
240
+ * is refused while the page holds unsaved changes (`useUnsavedChanges`), and
241
+ * the refusal names them so the panel can say where. Nothing is routed, so the
242
+ * draft stays exactly as it was. The person's own navigation (`initiator:
243
+ * "person"`, a link they clicked) is never refused here — sidebar parity — and
244
+ * neither is a shell-less target, which opens in a new tab and leaves this
245
+ * page, and its draft, alone. A caller that does not say who started it is
246
+ * treated as the assistant.
238
247
  */
239
248
  export declare function createAssistantNavigate(options: AssistantNavigateOptions): AssistantNavigate;
240
249
  /** The quota wall a `<product>:quota-exhausted` event names. */
@@ -1 +1 @@
1
- {"version":3,"file":"assistantOverlayState.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/assistantOverlayState.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"assistantOverlayState.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/assistantOverlayState.ts"],"names":[],"mappings":"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"}
@@ -1,72 +1,81 @@
1
+ import { unsavedChangesBlocking as e } from "../../navigation/unsavedChanges.js";
1
2
  //#region src/shared/assistant/ui/assistantOverlayState.ts
2
- function e(e) {
3
+ function t(e) {
3
4
  return {
4
5
  toggleEvent: `${e}:toggle-ai-assistant`,
5
6
  openStorageKey: `${e}:ai-panel:isOpen`,
6
7
  dockStorageKey: `${e}:ai-panel:docked`
7
8
  };
8
9
  }
9
- function t(e) {
10
+ function n(e) {
10
11
  if (typeof CustomEvent > "u" || !(e instanceof CustomEvent)) return null;
11
12
  let t = e.detail;
12
13
  return typeof t != "object" || !t || !("open" in t) ? null : typeof t.open == "boolean" ? t.open : null;
13
14
  }
14
- function n(e, t) {
15
+ function r(e, t) {
15
16
  return t ?? !e;
16
17
  }
17
- var r = "Ctrl+Shift+A";
18
- function i(e) {
18
+ var i = "Ctrl+Shift+A";
19
+ function a(e) {
19
20
  return (e.ctrlKey || e.metaKey) && e.shiftKey && typeof e.key == "string" && e.key.toLowerCase() === "a";
20
21
  }
21
- var a = "[role=\"dialog\"],[role=\"alertdialog\"],dialog[open]";
22
- function o(e, t) {
23
- return s(e) ? e.closest(t) : null;
22
+ var o = "[role=\"dialog\"],[role=\"alertdialog\"],dialog[open]";
23
+ function s(e, t) {
24
+ return c(e) ? e.closest(t) : null;
24
25
  }
25
- function s(e) {
26
+ function c(e) {
26
27
  return typeof e == "object" && !!e && "closest" in e && typeof e.closest == "function";
27
28
  }
28
- function c(e) {
29
+ function l(e) {
29
30
  return e.key !== "Escape" || !e.isOpen || e.alreadyHandled || e.dialogOpen || e.pressedInsideDialog || e.panelOwnsEscape ? "ignore" : "close";
30
31
  }
31
- var l = "max(var(--mobile-tabbar-height, 0px), var(--safe-bottom, 0px), env(safe-area-inset-bottom, 0px))";
32
- function u(e) {
33
- return `calc(${e} + ${l})`;
32
+ var u = "max(var(--mobile-tabbar-height, 0px), var(--safe-bottom, 0px), env(safe-area-inset-bottom, 0px))";
33
+ function d(e) {
34
+ return `calc(${e} + ${u})`;
34
35
  }
35
- var d = 440, f = "--assistant-dock-width", p = "--assistant-overlay-top", m = 56, h = "(min-width: 640px)";
36
- function g(e) {
36
+ var f = 440, p = "--assistant-dock-width", m = "--assistant-overlay-top", h = 56, g = "(min-width: 640px)";
37
+ function _(e) {
37
38
  return e.isOpen && e.docked && e.isDesktop ? 440 : 0;
38
39
  }
39
- var _ = 520, v = 24, y = "--assistant-panel-inset";
40
- function b(e) {
40
+ var v = 520, y = 24, b = "--assistant-panel-inset";
41
+ function x(e) {
41
42
  return !e.isOpen || !e.isDesktop ? 0 : e.docked ? 440 : 544;
42
43
  }
43
- var x = "fixed z-50 flex flex-col overflow-hidden border border-border-default bg-bg-surface shadow-2xl inset-x-0 bottom-0 top-auto rounded-t-2xl animate-in slide-in-from-bottom-4 fade-in duration-200", S = "h-[60vh] max-h-[60vh]", C = "h-[88vh] max-h-[88vh]", w = "sm:inset-auto sm:top-auto sm:bottom-24 sm:right-6 sm:rounded-2xl sm:h-[680px] sm:max-h-[calc(100vh-8rem)] sm:w-[520px] sm:max-w-[calc(100vw-2rem)]", T = "sm:left-auto sm:right-0 sm:top-[var(--assistant-overlay-top)] sm:bottom-0 sm:rounded-none sm:h-auto sm:max-h-none sm:w-[440px] sm:max-w-[calc(100vw-2rem)]";
44
- function E(e) {
44
+ var S = "fixed z-50 flex flex-col overflow-hidden border border-border-default bg-bg-surface shadow-2xl inset-x-0 bottom-0 top-auto rounded-t-2xl animate-in slide-in-from-bottom-4 fade-in duration-200", C = "h-[60vh] max-h-[60vh]", w = "h-[88vh] max-h-[88vh]", T = "sm:inset-auto sm:top-auto sm:bottom-24 sm:right-6 sm:rounded-2xl sm:h-[680px] sm:max-h-[calc(100vh-8rem)] sm:w-[520px] sm:max-w-[calc(100vw-2rem)]", E = "sm:left-auto sm:right-0 sm:top-[var(--assistant-overlay-top)] sm:bottom-0 sm:rounded-none sm:h-auto sm:max-h-none sm:w-[440px] sm:max-w-[calc(100vw-2rem)]";
45
+ function D(e) {
45
46
  return [
46
- x,
47
- e.expanded ? C : S,
48
- e.docked ? T : w
47
+ S,
48
+ e.expanded ? w : C,
49
+ e.docked ? E : T
49
50
  ].join(" ");
50
51
  }
51
- function D(e) {
52
- return (t) => e.isShellLessTarget?.(t) ? (e.openInNewTab(t), { kind: "new-tab" }) : (e.navigate(t), e.isDesktop() || e.collapseSheet(), { kind: "routed" });
52
+ function O(t) {
53
+ return (n, r) => {
54
+ if (t.isShellLessTarget?.(n)) return t.openInNewTab(n), { kind: "new-tab" };
55
+ let i = e(r);
56
+ return i ? {
57
+ kind: "refused",
58
+ reason: "unsaved-changes",
59
+ unsaved: i
60
+ } : (t.navigate(n), t.isDesktop() || t.collapseSheet(), { kind: "routed" });
61
+ };
53
62
  }
54
- function O(e) {
63
+ function k(e) {
55
64
  if (typeof CustomEvent > "u" || !(e instanceof CustomEvent)) return "generic";
56
65
  let t = e.detail;
57
66
  return typeof t != "object" || !t || !("kind" in t) ? "generic" : t.kind === "sandbox" || t.kind === "ai-credits" ? t.kind : "generic";
58
67
  }
59
- function k(e, t) {
68
+ function A(e, t) {
60
69
  try {
61
70
  return e()?.getItem(t) === "1";
62
71
  } catch {
63
72
  return !1;
64
73
  }
65
74
  }
66
- function A(e, t, n) {
75
+ function j(e, t, n) {
67
76
  try {
68
77
  e()?.setItem(t, n ? "1" : "0");
69
78
  } catch {}
70
79
  }
71
80
  //#endregion
72
- export { l as ASSISTANT_BOTTOM_CHROME_CLEARANCE, a as ASSISTANT_DIALOG_SELECTOR, T as ASSISTANT_DOCKED_DESKTOP_CLASS, d as ASSISTANT_DOCK_WIDTH_PX, f as ASSISTANT_DOCK_WIDTH_VAR, w as ASSISTANT_FLOATING_DESKTOP_CLASS, v as ASSISTANT_FLOATING_RIGHT_PX, _ as ASSISTANT_FLOATING_WIDTH_PX, m as ASSISTANT_OVERLAY_DEFAULT_TOP_PX, h as ASSISTANT_OVERLAY_DESKTOP_QUERY, p as ASSISTANT_OVERLAY_TOP_VAR, y as ASSISTANT_PANEL_INSET_VAR, x as ASSISTANT_SHEET_BASE_CLASS, S as ASSISTANT_SHEET_COMPACT_CLASS, C as ASSISTANT_SHEET_EXPANDED_CLASS, r as ASSISTANT_TOGGLE_SHORTCUT_LABEL, u as aboveAssistantBottomChrome, E as assistantOverlayClassName, c as assistantOverlayEscapeAction, e as assistantOverlayKeys, O as assistantQuotaKindOf, o as closestAround, D as createAssistantNavigate, i as isAssistantToggleShortcut, n as nextAssistantOpenState, g as publishedAssistantDockWidth, b as publishedAssistantPanelInset, k as readAssistantOverlayFlag, t as requestedAssistantOpenState, A as writeAssistantOverlayFlag };
81
+ export { u as ASSISTANT_BOTTOM_CHROME_CLEARANCE, o as ASSISTANT_DIALOG_SELECTOR, E as ASSISTANT_DOCKED_DESKTOP_CLASS, f as ASSISTANT_DOCK_WIDTH_PX, p as ASSISTANT_DOCK_WIDTH_VAR, T as ASSISTANT_FLOATING_DESKTOP_CLASS, y as ASSISTANT_FLOATING_RIGHT_PX, v as ASSISTANT_FLOATING_WIDTH_PX, h as ASSISTANT_OVERLAY_DEFAULT_TOP_PX, g as ASSISTANT_OVERLAY_DESKTOP_QUERY, m as ASSISTANT_OVERLAY_TOP_VAR, b as ASSISTANT_PANEL_INSET_VAR, S as ASSISTANT_SHEET_BASE_CLASS, C as ASSISTANT_SHEET_COMPACT_CLASS, w as ASSISTANT_SHEET_EXPANDED_CLASS, i as ASSISTANT_TOGGLE_SHORTCUT_LABEL, d as aboveAssistantBottomChrome, D as assistantOverlayClassName, l as assistantOverlayEscapeAction, t as assistantOverlayKeys, k as assistantQuotaKindOf, s as closestAround, O as createAssistantNavigate, a as isAssistantToggleShortcut, r as nextAssistantOpenState, _ as publishedAssistantDockWidth, x as publishedAssistantPanelInset, A as readAssistantOverlayFlag, n as requestedAssistantOpenState, j as writeAssistantOverlayFlag };
@@ -1 +1 @@
1
- {"version":3,"file":"AssistantConnectSourceItem.d.ts","sourceRoot":"","sources":["../../../../../src/shared/assistant/ui/composer/AssistantConnectSourceItem.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AACH,OAAO,EAAe,KAAK,EAAE,EAAmB,MAAM,OAAO,CAAC;AAc9D;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,uBAAuB,CACrC,IAAI,EAAE,MAAM,IAAI,EAChB,UAAU,CAAC,EAAE,MAAM,IAAI,GACtB,MAAM,IAAI,CAKZ;AAED;;;;;;;;;;;;GAYG;AACH,MAAM,MAAM,kCAAkC,GAAG,UAAU,GAAG,QAAQ,CAAC;AAoBvE,MAAM,WAAW,+BAA+B;IAC9C,2EAA2E;IAC3E,UAAU,CAAC,EAAE,MAAM,IAAI,CAAC;IACxB,6DAA6D;IAC7D,YAAY,CAAC,EAAE,kCAAkC,CAAC;CACnD;AAED,eAAO,MAAM,0BAA0B,EAAE,EAAE,CAAC,+BAA+B,CA6F1E,CAAC"}
1
+ {"version":3,"file":"AssistantConnectSourceItem.d.ts","sourceRoot":"","sources":["../../../../../src/shared/assistant/ui/composer/AssistantConnectSourceItem.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AACH,OAAO,EAAe,KAAK,EAAE,EAAmB,MAAM,OAAO,CAAC;AAc9D;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,uBAAuB,CACrC,IAAI,EAAE,MAAM,IAAI,EAChB,UAAU,CAAC,EAAE,MAAM,IAAI,GACtB,MAAM,IAAI,CAKZ;AAED;;;;;;;;;;;;GAYG;AACH,MAAM,MAAM,kCAAkC,GAAG,UAAU,GAAG,QAAQ,CAAC;AAoBvE,MAAM,WAAW,+BAA+B;IAC9C,2EAA2E;IAC3E,UAAU,CAAC,EAAE,MAAM,IAAI,CAAC;IACxB,6DAA6D;IAC7D,YAAY,CAAC,EAAE,kCAAkC,CAAC;CACnD;AAED,eAAO,MAAM,0BAA0B,EAAE,EAAE,CAAC,+BAA+B,CA8F1E,CAAC"}
@@ -16,7 +16,7 @@ var d = "flex w-full items-center gap-2.5 border-t border-border-subtle px-3 py-
16
16
  action: "assistant-connect-source-action"
17
17
  }, m = ({ onActivate: m, presentation: h = "menuitem" }) => {
18
18
  let g = e(), { href: _, open: v } = a(), y = r(), b = n(_), x = b === "internal" ? t(_) : null, S = o((e) => {
19
- e.defaultPrevented || e.button !== 0 || e.metaKey || e.ctrlKey || e.shiftKey || e.altKey || (m?.(), !(!y || !x) && (e.preventDefault(), y(x)));
19
+ e.defaultPrevented || e.button !== 0 || e.metaKey || e.ctrlKey || e.shiftKey || e.altKey || (m?.(), !(!y || !x) && (e.preventDefault(), y(x, "person")));
20
20
  }, [
21
21
  y,
22
22
  x,
@@ -83,6 +83,11 @@ interface Props {
83
83
  closeLabel: string;
84
84
  onClose: () => void;
85
85
  } | null;
86
+ /**
87
+ * ★ BOFF-8060 (N3): drawn under one assistant turn in the transcript drawer
88
+ * — the page the model offered in that voice turn.
89
+ */
90
+ renderAfterTurn?: (turnId: string) => ReactNode;
86
91
  }
87
92
  /**
88
93
  * Full-screen voice conversation (BOFF-7120).
@@ -1 +1 @@
1
- {"version":3,"file":"AssistantVoiceSession.d.ts","sourceRoot":"","sources":["../../../../../src/shared/assistant/ui/voice/AssistantVoiceSession.tsx"],"names":[],"mappings":"AAAA,OAAO,EAML,KAAK,EAAE,EACP,KAAK,SAAS,EACf,MAAM,OAAO,CAAC;AAMf,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,mBAAmB,CAAC;AAS7D,OAAO,KAAK,EAAE,6BAA6B,EAAE,MAAM,6CAA6C,CAAC;AAqBjG,OAAO,EAEL,KAAK,oBAAoB,EAC1B,MAAM,0BAA0B,CAAC;AAElC,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAC7D,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,4BAA4B,CAAC;AAEtE,gFAAgF;AAChF,MAAM,MAAM,SAAS,GAAG,MAAM,GAAG,OAAO,GAAG,MAAM,CAAC;AAElD,UAAU,KAAK;IACb,OAAO,EAAE,oBAAoB,CAAC;IAC9B,iEAAiE;IACjE,KAAK,CAAC,EAAE,aAAa,CAAC,mBAAmB,CAAC,CAAC;IAC3C,wCAAwC;IACxC,gBAAgB,CAAC,EAAE,MAAM,IAAI,CAAC;IAC9B,6EAA6E;IAC7E,gBAAgB,CAAC,EAAE,MAAM,IAAI,CAAC;IAC9B,uCAAuC;IACvC,WAAW,CAAC,EAAE,MAAM,IAAI,CAAC;IACzB,6EAA6E;IAC7E,MAAM,CAAC,EAAE,kBAAkB,GAAG,IAAI,CAAC;IACnC;;;;OAIG;IACH,aAAa,CAAC,EAAE,6BAA6B,GAAG,IAAI,CAAC;IACrD,gEAAgE;IAChE,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,YAAY,EAAE,MAAM,IAAI,CAAC;IACzB;;;;;;OAMG;IACH,WAAW,CAAC,EAAE,mBAAmB,EAAE,CAAC;IACpC,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,QAAQ,GAAG,IAAI,KAAK,IAAI,CAAC;IACjD,kBAAkB,CAAC,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1C,iBAAiB,CAAC,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,IAAI,CAAC;IACzC,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,0EAA0E;IAC1E,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAC9B,4DAA4D;IAC5D,YAAY,CAAC,EAAE;QAAE,MAAM,EAAE,MAAM,EAAE,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;IAC1D,KAAK,EAAE,MAAM,IAAI,CAAC;IAClB,mFAAmF;IACnF,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,0EAA0E;IAC1E,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,6DAA6D;IAC7D,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B;;;OAGG;IACH,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB;;;OAGG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,+DAA+D;IAC/D,aAAa,CAAC,EAAE,MAAM,IAAI,CAAC;IAC3B,oDAAoD;IACpD,QAAQ,CAAC,EAAE,MAAM,IAAI,CAAC;IACtB;;;;;OAKG;IACH,YAAY,CAAC,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,MAAM,IAAI,CAAA;KAAE,GAAG,IAAI,CAAC;IAC5D,6EAA6E;IAC7E,YAAY,CAAC,EAAE;QACb,OAAO,EAAE,SAAS,CAAC;QACnB,UAAU,EAAE,MAAM,CAAC;QACnB,OAAO,EAAE,MAAM,IAAI,CAAC;KACrB,GAAG,IAAI,CAAC;CACV;AAED;;;;;;;;;;;;;;;;;;GAkBG;AACH,eAAO,MAAM,qBAAqB,EAAE,EAAE,CAAC,KAAK,CA41B3C,CAAC"}
1
+ {"version":3,"file":"AssistantVoiceSession.d.ts","sourceRoot":"","sources":["../../../../../src/shared/assistant/ui/voice/AssistantVoiceSession.tsx"],"names":[],"mappings":"AAAA,OAAO,EAML,KAAK,EAAE,EACP,KAAK,SAAS,EACf,MAAM,OAAO,CAAC;AAMf,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,mBAAmB,CAAC;AAS7D,OAAO,KAAK,EAAE,6BAA6B,EAAE,MAAM,6CAA6C,CAAC;AAqBjG,OAAO,EAEL,KAAK,oBAAoB,EAC1B,MAAM,0BAA0B,CAAC;AAElC,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAC7D,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,4BAA4B,CAAC;AAEtE,gFAAgF;AAChF,MAAM,MAAM,SAAS,GAAG,MAAM,GAAG,OAAO,GAAG,MAAM,CAAC;AAElD,UAAU,KAAK;IACb,OAAO,EAAE,oBAAoB,CAAC;IAC9B,iEAAiE;IACjE,KAAK,CAAC,EAAE,aAAa,CAAC,mBAAmB,CAAC,CAAC;IAC3C,wCAAwC;IACxC,gBAAgB,CAAC,EAAE,MAAM,IAAI,CAAC;IAC9B,6EAA6E;IAC7E,gBAAgB,CAAC,EAAE,MAAM,IAAI,CAAC;IAC9B,uCAAuC;IACvC,WAAW,CAAC,EAAE,MAAM,IAAI,CAAC;IACzB,6EAA6E;IAC7E,MAAM,CAAC,EAAE,kBAAkB,GAAG,IAAI,CAAC;IACnC;;;;OAIG;IACH,aAAa,CAAC,EAAE,6BAA6B,GAAG,IAAI,CAAC;IACrD,gEAAgE;IAChE,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,YAAY,EAAE,MAAM,IAAI,CAAC;IACzB;;;;;;OAMG;IACH,WAAW,CAAC,EAAE,mBAAmB,EAAE,CAAC;IACpC,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,QAAQ,GAAG,IAAI,KAAK,IAAI,CAAC;IACjD,kBAAkB,CAAC,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1C,iBAAiB,CAAC,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,IAAI,CAAC;IACzC,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,0EAA0E;IAC1E,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAC9B,4DAA4D;IAC5D,YAAY,CAAC,EAAE;QAAE,MAAM,EAAE,MAAM,EAAE,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;IAC1D,KAAK,EAAE,MAAM,IAAI,CAAC;IAClB,mFAAmF;IACnF,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,0EAA0E;IAC1E,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,6DAA6D;IAC7D,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B;;;OAGG;IACH,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB;;;OAGG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,+DAA+D;IAC/D,aAAa,CAAC,EAAE,MAAM,IAAI,CAAC;IAC3B,oDAAoD;IACpD,QAAQ,CAAC,EAAE,MAAM,IAAI,CAAC;IACtB;;;;;OAKG;IACH,YAAY,CAAC,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,MAAM,IAAI,CAAA;KAAE,GAAG,IAAI,CAAC;IAC5D,6EAA6E;IAC7E,YAAY,CAAC,EAAE;QACb,OAAO,EAAE,SAAS,CAAC;QACnB,UAAU,EAAE,MAAM,CAAC;QACnB,OAAO,EAAE,MAAM,IAAI,CAAC;KACrB,GAAG,IAAI,CAAC;IACT;;;OAGG;IACH,eAAe,CAAC,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,SAAS,CAAC;CACjD;AAED;;;;;;;;;;;;;;;;;;GAkBG;AACH,eAAO,MAAM,qBAAqB,EAAE,EAAE,CAAC,KAAK,CA81B3C,CAAC"}
@@ -17,7 +17,7 @@ import { useCallback as s, useEffect as c, useMemo as me, useRef as l, useState
17
17
  import { Maximize2 as he, Minimize2 as ge, ScrollText as _e, X as d } from "lucide-react";
18
18
  import { jsx as f, jsxs as p } from "react/jsx-runtime";
19
19
  //#region src/shared/assistant/ui/voice/AssistantVoiceSession.tsx
20
- var m = ({ session: m, turns: be = [], onSaveTranscript: xe, onContinueInChat: Se, notice: h = null, privacyNotice: g = null, spoken: _, onInterrupt: Ce, onToggleMute: v, attachments: y = [], onAttachFiles: b, onRemoveAttachment: we, onRetryAttachment: Te, canAttachMore: Ee = !0, preparingAttachments: x = 0, spokenChunks: S = null, onEnd: C, capturing: De = !0, interrupting: Oe = !1, awaitingEndpoint: ke = !1, holding: w = !1, correcting: Ae = !1, onLetMeFinish: T, onImDone: E, proposalChip: D = null, proposalTray: O = null }) => {
20
+ var m = ({ session: m, turns: be = [], onSaveTranscript: xe, onContinueInChat: Se, notice: h = null, privacyNotice: g = null, spoken: _, onInterrupt: Ce, onToggleMute: v, attachments: y = [], onAttachFiles: b, onRemoveAttachment: we, onRetryAttachment: Te, canAttachMore: Ee = !0, preparingAttachments: x = 0, spokenChunks: S = null, onEnd: C, capturing: De = !0, interrupting: Oe = !1, awaitingEndpoint: ke = !1, holding: w = !1, correcting: Ae = !1, onLetMeFinish: T, onImDone: E, proposalChip: D = null, proposalTray: O = null, renderAfterTurn: je }) => {
21
21
  let k = n(), { muted: A, error: j } = m, M = l(null), N = l(null), [P, F] = u("mini"), I = P === "full", L = P === "mini", R = P === "mini" ? "panel" : P === "panel" ? "full" : "mini", [z, B] = u(!1);
22
22
  t("assistant.transcript", me(() => ({ run: () => z ? { status: "already" } : (B(!0), { status: "done" }) }), [z]));
23
23
  let V = O !== null && !L, H = l(!1), U = l(v);
@@ -26,7 +26,7 @@ var m = ({ session: m, turns: be = [], onSaveTranscript: xe, onContinueInChat: S
26
26
  m.phase !== "listening" && m.phase !== "thinking" || A || H.current || o(m) || (H.current = !0, U.current());
27
27
  }, [A, m]), G = s(() => {
28
28
  H.current && (H.current = !1, U.current());
29
- }, []), je = W;
29
+ }, []), Me = W;
30
30
  c(() => {
31
31
  let e = () => {
32
32
  document.visibilityState === "hidden" ? W() : G();
@@ -84,7 +84,7 @@ var m = ({ session: m, turns: be = [], onSaveTranscript: xe, onContinueInChat: S
84
84
  capturing: De,
85
85
  interrupting: Oe,
86
86
  awaitingEndpoint: ke
87
- }), Me = (() => {
87
+ }), Ne = (() => {
88
88
  switch (X) {
89
89
  case "connecting": return k("voiceSession.connecting", "Starting the microphone…");
90
90
  case "endpoint-grace": return k("voiceSession.endpointGrace", "Still listening — take your time");
@@ -96,12 +96,12 @@ var m = ({ session: m, turns: be = [], onSaveTranscript: xe, onContinueInChat: S
96
96
  case "listening": return A ? k("voiceSession.muted", "Microphone off") : k("voiceSession.listening", "Listening…");
97
97
  default: return X;
98
98
  }
99
- })(), Z = !A && (X === "listening" || X === "endpoint-grace"), Q = Z && w ? k("voiceSession.holding", "Take your time — tap “I’m done” when you finish") : Z && Ae ? k("voiceSession.correcting", "Stopped that answer — listening to your correction") : Me, $ = ne({
99
+ })(), Z = !A && (X === "listening" || X === "endpoint-grace"), Q = Z && w ? k("voiceSession.holding", "Take your time — tap “I’m done” when you finish") : Z && Ae ? k("voiceSession.correcting", "Stopped that answer — listening to your correction") : Ne, $ = ne({
100
100
  tr: k,
101
101
  stage: X,
102
102
  muted: A,
103
103
  label: Q
104
- }), Ne = te(Q, $), Pe = X === "thinking";
104
+ }), Pe = te(Q, $), Fe = X === "thinking";
105
105
  return /* @__PURE__ */ p("div", {
106
106
  ref: N,
107
107
  className: `flex flex-col items-center justify-between bg-bg-sunken ${P === "full" ? "fixed inset-x-0 bottom-0 top-14 z-[60] px-6 py-8" : P === "panel" ? "absolute inset-0 z-20 px-4 py-6" : "absolute inset-x-0 bottom-0 z-20 h-[11.25rem] border-t border-border-subtle px-3 py-3 shadow-lg"}`,
@@ -157,9 +157,9 @@ var m = ({ session: m, turns: be = [], onSaveTranscript: xe, onContinueInChat: S
157
157
  spokenChunks: S,
158
158
  state: X,
159
159
  caption: i,
160
- statusText: Ne,
160
+ statusText: Pe,
161
161
  statusSuffix: $,
162
- rotateStatus: Pe,
162
+ rotateStatus: Fe,
163
163
  errorText: a,
164
164
  control: n
165
165
  }) : /* @__PURE__ */ f(le, {
@@ -168,9 +168,9 @@ var m = ({ session: m, turns: be = [], onSaveTranscript: xe, onContinueInChat: S
168
168
  spokenChunks: S,
169
169
  assistantCaption: _,
170
170
  expanded: I,
171
- statusText: Ne,
171
+ statusText: Pe,
172
172
  statusSuffix: $,
173
- rotateStatus: Pe,
173
+ rotateStatus: Fe,
174
174
  errorText: a,
175
175
  control: n
176
176
  });
@@ -214,7 +214,8 @@ var m = ({ session: m, turns: be = [], onSaveTranscript: xe, onContinueInChat: S
214
214
  turns: be,
215
215
  onClose: () => B(!1),
216
216
  onSave: xe,
217
- onContinueInChat: Se
217
+ onContinueInChat: Se,
218
+ renderAfterTurn: je
218
219
  }) : null,
219
220
  b ? /* @__PURE__ */ f("div", {
220
221
  className: `absolute ${I ? "left-6 top-6" : L ? "left-11 top-2" : "left-3 top-3"}`,
@@ -222,7 +223,7 @@ var m = ({ session: m, turns: be = [], onSaveTranscript: xe, onContinueInChat: S
222
223
  onFiles: (e) => {
223
224
  b(e), F((e) => e === "mini" ? "panel" : e);
224
225
  },
225
- onPickerOpen: je,
226
+ onPickerOpen: Me,
226
227
  direction: "down",
227
228
  canAddMore: Ee
228
229
  })
@@ -1,4 +1,4 @@
1
- import { FC } from 'react';
1
+ import { FC, ReactNode } from 'react';
2
2
  import { VoiceTranscriptTurn } from '../../voice/turnVisibility';
3
3
  /**
4
4
  * The voice conversation, as a normal chat.
@@ -32,6 +32,11 @@ interface Props {
32
32
  * leading group rather than being scattered one divider apart.
33
33
  */
34
34
  turns: ReadonlyArray<VoiceTranscriptTurn>;
35
+ /**
36
+ * ★ BOFF-8060 (N3): drawn under one ASSISTANT turn's text — the page the
37
+ * model offered in that voice turn. Absent, or null for a turn, nothing is.
38
+ */
39
+ renderAfterTurn?: (turnId: string) => ReactNode;
35
40
  }
36
41
  export declare const VoiceConversationView: FC<Props>;
37
42
  export {};
@@ -1 +1 @@
1
- {"version":3,"file":"VoiceConversationView.d.ts","sourceRoot":"","sources":["../../../../../src/shared/assistant/ui/voice/VoiceConversationView.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAW,KAAK,EAAE,EAAE,MAAM,OAAO,CAAC;AAEzC,OAAO,EAEL,KAAK,mBAAmB,EACzB,MAAM,4BAA4B,CAAC;AAGpC;;;;;;;;;;;;;;;;;;;;;;GAsBG;AAEH,UAAU,KAAK;IACb;;;;;;OAMG;IACH,KAAK,EAAE,aAAa,CAAC,mBAAmB,CAAC,CAAC;CAC3C;AAED,eAAO,MAAM,qBAAqB,EAAE,EAAE,CAAC,KAAK,CAwE3C,CAAC"}
1
+ {"version":3,"file":"VoiceConversationView.d.ts","sourceRoot":"","sources":["../../../../../src/shared/assistant/ui/voice/VoiceConversationView.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAW,KAAK,EAAE,EAAE,KAAK,SAAS,EAAE,MAAM,OAAO,CAAC;AAEzD,OAAO,EAEL,KAAK,mBAAmB,EACzB,MAAM,4BAA4B,CAAC;AAGpC;;;;;;;;;;;;;;;;;;;;;;GAsBG;AAEH,UAAU,KAAK;IACb;;;;;;OAMG;IACH,KAAK,EAAE,aAAa,CAAC,mBAAmB,CAAC,CAAC;IAC1C;;;OAGG;IACH,eAAe,CAAC,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,SAAS,CAAC;CACjD;AAED,eAAO,MAAM,qBAAqB,EAAE,EAAE,CAAC,KAAK,CA4E3C,CAAC"}
@@ -4,18 +4,18 @@ import { groupConsecutiveBySession as n } from "../../voice/turnVisibility.js";
4
4
  import { useMemo as r } from "react";
5
5
  import { jsx as i, jsxs as a } from "react/jsx-runtime";
6
6
  //#region src/shared/assistant/ui/voice/VoiceConversationView.tsx
7
- var o = ({ turns: o }) => {
8
- let s = e(), c = r(() => n(o, (e) => e.sessionId), [o]);
7
+ var o = ({ turns: o, renderAfterTurn: s }) => {
8
+ let c = e(), l = r(() => n(o, (e) => e.sessionId), [o]);
9
9
  return o.length === 0 ? /* @__PURE__ */ i("div", {
10
10
  className: "flex flex-1 items-center justify-center px-6",
11
11
  children: /* @__PURE__ */ i("p", {
12
12
  className: "text-center text-sm text-text-muted",
13
- children: s("voiceSession.transcriptEmpty", "Nothing spoken yet in this session.")
13
+ children: c("voiceSession.transcriptEmpty", "Nothing spoken yet in this session.")
14
14
  })
15
15
  }) : /* @__PURE__ */ i("div", {
16
16
  className: "scrollbar-slim flex-1 overflow-y-auto px-4 py-4",
17
17
  "data-testid": "assistant-voice-conversation",
18
- children: c.map((e, n) => /* @__PURE__ */ a("section", {
18
+ children: l.map((e, n) => /* @__PURE__ */ a("section", {
19
19
  className: "space-y-4 pb-4",
20
20
  children: [n > 0 ? /* @__PURE__ */ a("div", {
21
21
  className: "flex items-center gap-2 pt-2",
@@ -24,7 +24,7 @@ var o = ({ turns: o }) => {
24
24
  /* @__PURE__ */ i("span", { className: "h-px flex-1 bg-border-subtle" }),
25
25
  /* @__PURE__ */ i("span", {
26
26
  className: "text-[11px] uppercase tracking-wide text-text-muted",
27
- children: s("voiceSession.newSession", "New voice session")
27
+ children: c("voiceSession.newSession", "New voice session")
28
28
  }),
29
29
  /* @__PURE__ */ i("span", { className: "h-px flex-1 bg-border-subtle" })
30
30
  ]
@@ -34,9 +34,9 @@ var o = ({ turns: o }) => {
34
34
  className: "max-w-[85%] whitespace-pre-wrap break-words rounded-2xl bg-bg-elevated px-3 py-2 text-sm leading-relaxed text-text-primary",
35
35
  children: e.text
36
36
  })
37
- }, e.id) : /* @__PURE__ */ i("div", {
37
+ }, e.id) : /* @__PURE__ */ a("div", {
38
38
  className: "text-sm leading-relaxed text-text-secondary",
39
- children: /* @__PURE__ */ i(t, { content: e.text })
39
+ children: [/* @__PURE__ */ i(t, { content: e.text }), s?.(e.id)]
40
40
  }, e.id))]
41
41
  }, `${e.sessionId ?? "earlier"}-${n}`))
42
42
  });
@@ -1,4 +1,4 @@
1
- import { FC } from 'react';
1
+ import { FC, ReactNode } from 'react';
2
2
  import { VoiceTranscriptTurn } from '../../voice/turnVisibility';
3
3
  /**
4
4
  * This session's spoken turns, on demand.
@@ -56,6 +56,11 @@ interface Props {
56
56
  onShowEarlier?: () => void;
57
57
  /** A page is being read: the control waits. */
58
58
  showEarlierDisabled?: boolean;
59
+ /**
60
+ * ★ BOFF-8060 (N3): what goes under one assistant turn — the page the model
61
+ * offered in that VOICE turn. Never the chat thread's offers (rule 4).
62
+ */
63
+ renderAfterTurn?: (turnId: string) => ReactNode;
59
64
  }
60
65
  export declare const VoiceTranscriptDrawer: FC<Props>;
61
66
  export {};
@@ -1 +1 @@
1
- {"version":3,"file":"VoiceTranscriptDrawer.d.ts","sourceRoot":"","sources":["../../../../../src/shared/assistant/ui/voice/VoiceTranscriptDrawer.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAqB,KAAK,EAAE,EAAE,MAAM,OAAO,CAAC;AAOnD,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,4BAA4B,CAAC;AAEtE;;;;;;;;;;;;;;;;;;GAkBG;AAEH,UAAU,KAAK;IACb,KAAK,EAAE,aAAa,CAAC,mBAAmB,CAAC,CAAC;IAC1C,OAAO,EAAE,MAAM,IAAI,CAAC;IACpB,8EAA8E;IAC9E,MAAM,CAAC,EAAE,MAAM,IAAI,CAAC;IACpB;;;;;;;;;;;;OAYG;IACH,gBAAgB,CAAC,EAAE,MAAM,IAAI,CAAC;IAC9B;;;;;;;OAOG;IACH,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB;;;;;OAKG;IACH,aAAa,CAAC,EAAE,MAAM,IAAI,CAAC;IAC3B,+CAA+C;IAC/C,mBAAmB,CAAC,EAAE,OAAO,CAAC;CAC/B;AAED,eAAO,MAAM,qBAAqB,EAAE,EAAE,CAAC,KAAK,CAoJ3C,CAAC"}
1
+ {"version":3,"file":"VoiceTranscriptDrawer.d.ts","sourceRoot":"","sources":["../../../../../src/shared/assistant/ui/voice/VoiceTranscriptDrawer.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAqB,KAAK,EAAE,EAAE,KAAK,SAAS,EAAE,MAAM,OAAO,CAAC;AAOnE,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,4BAA4B,CAAC;AAEtE;;;;;;;;;;;;;;;;;;GAkBG;AAEH,UAAU,KAAK;IACb,KAAK,EAAE,aAAa,CAAC,mBAAmB,CAAC,CAAC;IAC1C,OAAO,EAAE,MAAM,IAAI,CAAC;IACpB,8EAA8E;IAC9E,MAAM,CAAC,EAAE,MAAM,IAAI,CAAC;IACpB;;;;;;;;;;;;OAYG;IACH,gBAAgB,CAAC,EAAE,MAAM,IAAI,CAAC;IAC9B;;;;;;;OAOG;IACH,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB;;;;;OAKG;IACH,aAAa,CAAC,EAAE,MAAM,IAAI,CAAC;IAC3B,+CAA+C;IAC/C,mBAAmB,CAAC,EAAE,OAAO,CAAC;IAC9B;;;OAGG;IACH,eAAe,CAAC,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,SAAS,CAAC;CACjD;AAED,eAAO,MAAM,qBAAqB,EAAE,EAAE,CAAC,KAAK,CAqJ3C,CAAC"}