botframework-webchat-component 4.14.0 → 4.15.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.
Files changed (453) hide show
  1. package/.eslintrc.yml +4 -106
  2. package/.prettierrc.yml +1 -1
  3. package/lib/Activity/Bubble.js +2 -2
  4. package/lib/Activity/CarouselFilmStrip.js +3 -3
  5. package/lib/Activity/CarouselFilmStripAttachment.js +2 -2
  6. package/lib/Activity/CarouselLayout.js +5 -5
  7. package/lib/Activity/Speak.js +6 -6
  8. package/lib/Activity/StackedLayout.d.ts.map +1 -1
  9. package/lib/Activity/StackedLayout.js +3 -3
  10. package/lib/Assets/TypingAnimation.js +2 -2
  11. package/lib/Attachment/AudioAttachment.js +2 -2
  12. package/lib/Attachment/AudioContent.js +2 -2
  13. package/lib/Attachment/FileAttachment.js +2 -2
  14. package/lib/Attachment/FileContent.d.ts.map +1 -1
  15. package/lib/Attachment/FileContent.js +12 -2
  16. package/lib/Attachment/HTMLVideoContent.js +2 -2
  17. package/lib/Attachment/ImageContent.js +2 -2
  18. package/lib/Attachment/TextContent.js +2 -2
  19. package/lib/Attachment/VideoAttachment.js +2 -2
  20. package/lib/Attachment/VideoContent.js +1 -1
  21. package/lib/Attachment/VimeoContent.js +2 -2
  22. package/lib/Attachment/YouTubeContent.js +2 -2
  23. package/lib/Avatar/ImageAvatar.js +2 -2
  24. package/lib/Avatar/InitialsAvatar.js +2 -2
  25. package/lib/BasicConnectivityStatus.js +2 -2
  26. package/lib/BasicSendBox.js +3 -3
  27. package/lib/BasicToast.js +4 -4
  28. package/lib/BasicToaster.js +8 -5
  29. package/lib/BasicTranscript.d.ts +7 -0
  30. package/lib/BasicTranscript.d.ts.map +1 -0
  31. package/lib/BasicTranscript.js +387 -729
  32. package/lib/BasicTypingIndicator.d.ts +2 -1
  33. package/lib/BasicTypingIndicator.d.ts.map +1 -1
  34. package/lib/BasicTypingIndicator.js +13 -5
  35. package/lib/BasicWebChat.js +2 -2
  36. package/lib/Composer.d.ts.map +1 -1
  37. package/lib/Composer.js +42 -35
  38. package/lib/ConnectivityStatus/Assets/ErrorNotificationIcon.js +2 -2
  39. package/lib/ConnectivityStatus/Assets/SpinnerAnimation.js +2 -2
  40. package/lib/ConnectivityStatus/Assets/WarningNotificationIcon.js +2 -2
  41. package/lib/ConnectivityStatus/Connected.js +1 -1
  42. package/lib/ConnectivityStatus/Connecting.js +4 -4
  43. package/lib/ConnectivityStatus/FailedToConnect.js +2 -2
  44. package/lib/ConnectivityStatus/JavaScriptError.js +2 -2
  45. package/lib/Dictation.js +4 -4
  46. package/lib/ErrorBox.js +2 -2
  47. package/lib/Middleware/Activity/createCoreMiddleware.d.ts.map +1 -1
  48. package/lib/Middleware/Activity/createCoreMiddleware.js +1 -1
  49. package/lib/Middleware/ActivityStatus/AbsoluteTime.js +1 -1
  50. package/lib/Middleware/ActivityStatus/RelativeTime.js +1 -1
  51. package/lib/Middleware/ActivityStatus/SendStatus/SendFailedRetry.js +3 -3
  52. package/lib/Middleware/ActivityStatus/SendStatus/SendStatus.js +5 -5
  53. package/lib/Middleware/ActivityStatus/Timestamp.js +2 -2
  54. package/lib/Middleware/ActivityStatus/createSendStatusMiddleware.js +21 -16
  55. package/lib/Middleware/ActivityStatus/createTimestampMiddleware.js +1 -1
  56. package/lib/Middleware/Attachment/createCoreMiddleware.js +2 -5
  57. package/lib/Middleware/AttachmentForScreenReader/AudioAttachment.js +1 -1
  58. package/lib/Middleware/AttachmentForScreenReader/FileAttachment.js +1 -1
  59. package/lib/Middleware/AttachmentForScreenReader/ImageAttachment.js +1 -1
  60. package/lib/Middleware/AttachmentForScreenReader/TextAttachment.js +1 -1
  61. package/lib/Middleware/AttachmentForScreenReader/VideoAttachment.js +1 -1
  62. package/lib/Middleware/AttachmentForScreenReader/createCoreMiddleware.d.ts.map +1 -1
  63. package/lib/Middleware/AttachmentForScreenReader/createCoreMiddleware.js +1 -1
  64. package/lib/Middleware/Avatar/createCoreMiddleware.d.ts.map +1 -1
  65. package/lib/Middleware/Avatar/createCoreMiddleware.js +3 -4
  66. package/lib/Middleware/CardAction/createCoreMiddleware.js +10 -3
  67. package/lib/Middleware/GroupActivities/createCoreMiddleware.js +1 -1
  68. package/lib/Middleware/ScrollToEndButton/ScrollToEndButton.js +2 -2
  69. package/lib/Middleware/ScrollToEndButton/createScrollToEndButtonMiddleware.d.ts.map +1 -1
  70. package/lib/Middleware/ScrollToEndButton/createScrollToEndButtonMiddleware.js +1 -1
  71. package/lib/Middleware/Toast/createCoreMiddleware.d.ts.map +1 -1
  72. package/lib/Middleware/Toast/createCoreMiddleware.js +1 -1
  73. package/lib/Middleware/TypingIndicator/createCoreMiddleware.d.ts.map +1 -1
  74. package/lib/Middleware/TypingIndicator/createCoreMiddleware.js +9 -7
  75. package/lib/ReactWebChat.js +5 -3
  76. package/lib/ScreenReaderActivity.js +17 -8
  77. package/lib/ScreenReaderText.d.ts +9 -0
  78. package/lib/ScreenReaderText.d.ts.map +1 -0
  79. package/lib/ScreenReaderText.js +22 -8
  80. package/lib/SendBox/Assets/SendIcon.js +2 -2
  81. package/lib/SendBox/AutoResizeTextArea.js +4 -4
  82. package/lib/SendBox/DictationInterims.js +3 -3
  83. package/lib/SendBox/IconButton.d.ts +11 -0
  84. package/lib/SendBox/IconButton.d.ts.map +1 -0
  85. package/lib/SendBox/IconButton.js +27 -7
  86. package/lib/SendBox/MicrophoneButton.js +5 -5
  87. package/lib/SendBox/SendButton.js +5 -5
  88. package/lib/SendBox/SuggestedAction.d.ts +17 -0
  89. package/lib/SendBox/SuggestedAction.d.ts.map +1 -0
  90. package/lib/SendBox/SuggestedAction.js +28 -19
  91. package/lib/SendBox/SuggestedActions.d.ts.map +1 -1
  92. package/lib/SendBox/SuggestedActions.js +33 -12
  93. package/lib/SendBox/TextBox.js +6 -6
  94. package/lib/SendBox/UploadButton.js +6 -6
  95. package/lib/Styles/StyleSet/BasicTranscript.d.ts +13 -5
  96. package/lib/Styles/StyleSet/BasicTranscript.d.ts.map +1 -1
  97. package/lib/Styles/StyleSet/BasicTranscript.js +21 -9
  98. package/lib/Styles/StyleSet/Bubble.d.ts.map +1 -1
  99. package/lib/Styles/StyleSet/Bubble.js +2 -2
  100. package/lib/Styles/StyleSet/CarouselFilmStrip.d.ts.map +1 -1
  101. package/lib/Styles/StyleSet/CarouselFilmStrip.js +2 -2
  102. package/lib/Styles/StyleSet/CarouselFilmStripAttachment.d.ts.map +1 -1
  103. package/lib/Styles/StyleSet/CarouselFilmStripAttachment.js +2 -2
  104. package/lib/Styles/StyleSet/KeyboardHelp.d.ts +123 -0
  105. package/lib/Styles/StyleSet/KeyboardHelp.d.ts.map +1 -0
  106. package/lib/Styles/StyleSet/KeyboardHelp.js +145 -0
  107. package/lib/Styles/StyleSet/ScrollToEndButton.d.ts +1 -1
  108. package/lib/Styles/StyleSet/ScrollToEndButton.js +2 -2
  109. package/lib/Styles/StyleSet/SendBoxButton.d.ts +56 -10
  110. package/lib/Styles/StyleSet/SendBoxButton.d.ts.map +1 -1
  111. package/lib/Styles/StyleSet/SendBoxButton.js +76 -12
  112. package/lib/Styles/StyleSet/SendBoxTextBox.d.ts +1 -1
  113. package/lib/Styles/StyleSet/SendBoxTextBox.d.ts.map +1 -1
  114. package/lib/Styles/StyleSet/SendBoxTextBox.js +3 -3
  115. package/lib/Styles/StyleSet/StackedLayout.d.ts.map +1 -1
  116. package/lib/Styles/StyleSet/StackedLayout.js +1 -1
  117. package/lib/Styles/StyleSet/SuggestedAction.d.ts +73 -28
  118. package/lib/Styles/StyleSet/SuggestedAction.d.ts.map +1 -1
  119. package/lib/Styles/StyleSet/SuggestedAction.js +116 -41
  120. package/lib/Styles/StyleSet/SuggestedActions.d.ts +13 -6
  121. package/lib/Styles/StyleSet/SuggestedActions.d.ts.map +1 -1
  122. package/lib/Styles/StyleSet/SuggestedActions.js +13 -6
  123. package/lib/Styles/createStyleSet.d.ts +323 -54
  124. package/lib/Styles/createStyleSet.d.ts.map +1 -1
  125. package/lib/Styles/createStyleSet.js +5 -2
  126. package/lib/Styles/mirrorStyle.js +13 -4
  127. package/lib/Toast/NotificationIcon.js +7 -3
  128. package/lib/Toast/createToastMiddleware.d.ts.map +1 -1
  129. package/lib/Toast/createToastMiddleware.js +1 -1
  130. package/lib/Transcript/ActivityRow.d.ts +9 -0
  131. package/lib/Transcript/ActivityRow.d.ts.map +1 -0
  132. package/lib/Transcript/ActivityRow.js +157 -0
  133. package/lib/Transcript/ActivityTextAlt.js +57 -0
  134. package/lib/Transcript/FocusTrap.d.ts +8 -0
  135. package/lib/Transcript/FocusTrap.d.ts.map +1 -0
  136. package/lib/Transcript/FocusTrap.js +74 -0
  137. package/lib/Transcript/KeyboardHelp.d.ts +4 -0
  138. package/lib/Transcript/KeyboardHelp.d.ts.map +1 -0
  139. package/lib/Transcript/KeyboardHelp.js +550 -0
  140. package/lib/Transcript/LiveRegionTranscript.d.ts +8 -0
  141. package/lib/Transcript/LiveRegionTranscript.d.ts.map +1 -0
  142. package/lib/Transcript/LiveRegionTranscript.js +214 -0
  143. package/lib/Transcript/types.d.ts +2 -0
  144. package/lib/Transcript/types.d.ts.map +1 -0
  145. package/lib/Transcript/types.js +2 -0
  146. package/lib/Transcript/useActivityAccessibleName.d.ts +4 -0
  147. package/lib/Transcript/useActivityAccessibleName.d.ts.map +1 -0
  148. package/lib/Transcript/useActivityAccessibleName.js +97 -0
  149. package/lib/Utils/AccessKeySink/Surface.js +7 -5
  150. package/lib/Utils/AccessibleButton.d.ts +11 -0
  151. package/lib/Utils/AccessibleButton.d.ts.map +1 -0
  152. package/lib/Utils/AccessibleButton.js +15 -8
  153. package/lib/Utils/AccessibleInputText.js +6 -4
  154. package/lib/Utils/AccessibleTextArea.js +6 -4
  155. package/lib/Utils/CroppedImage.js +2 -2
  156. package/lib/Utils/Fade.js +2 -2
  157. package/lib/Utils/FocusRedirector.d.ts +9 -0
  158. package/lib/Utils/FocusRedirector.d.ts.map +1 -0
  159. package/lib/Utils/FocusRedirector.js +18 -15
  160. package/lib/Utils/InlineMarkdown.js +17 -10
  161. package/lib/Utils/TypeFocusSink/FocusBox.js +6 -4
  162. package/lib/Utils/TypeFocusSink/getTabIndex.js +1 -1
  163. package/lib/Utils/TypeFocusSink/inputtableKey.d.ts +2 -0
  164. package/lib/Utils/TypeFocusSink/inputtableKey.d.ts.map +1 -0
  165. package/lib/Utils/TypeFocusSink/inputtableKey.js +5 -2
  166. package/lib/Utils/TypeFocusSink/navigableEvent.js +1 -1
  167. package/lib/Utils/activityAltText.d.ts +8 -0
  168. package/lib/Utils/activityAltText.d.ts.map +1 -0
  169. package/lib/Utils/activityAltText.js +2 -2
  170. package/lib/Utils/addTargetBlankToHyperlinksMarkdown.js +1 -1
  171. package/lib/Utils/createCustomEvent.js +9 -3
  172. package/lib/Utils/debounce.js +1 -1
  173. package/lib/Utils/detectBrowser.js +4 -2
  174. package/lib/Utils/downscaleImageToDataURL/downscaleImageToDataURLUsingWorker.js +3 -3
  175. package/lib/Utils/downscaleImageToDataURL/index.js +2 -2
  176. package/lib/Utils/filterMap.js +1 -1
  177. package/lib/Utils/findAncestor.js +17 -0
  178. package/lib/Utils/getActivityUniqueId.js +4 -2
  179. package/lib/Utils/intersectionOf.d.ts +5 -0
  180. package/lib/Utils/intersectionOf.d.ts.map +1 -0
  181. package/lib/Utils/intersectionOf.js +17 -2
  182. package/lib/Utils/isZeroOrPositive.d.ts +5 -0
  183. package/lib/Utils/isZeroOrPositive.d.ts.map +1 -0
  184. package/lib/Utils/isZeroOrPositive.js +4 -1
  185. package/lib/Utils/mapMap.js +10 -3
  186. package/lib/Utils/readDataURIToBlob.js +3 -3
  187. package/lib/Utils/scrollIntoViewWithBlockNearest.d.ts +7 -0
  188. package/lib/Utils/scrollIntoViewWithBlockNearest.d.ts.map +1 -0
  189. package/lib/Utils/scrollIntoViewWithBlockNearest.js +48 -0
  190. package/lib/Utils/shallowEquals.js +7 -3
  191. package/lib/Utils/supportPseudoClass.d.ts +2 -0
  192. package/lib/Utils/supportPseudoClass.d.ts.map +1 -0
  193. package/lib/Utils/supportPseudoClass.js +23 -0
  194. package/lib/Utils/tabbableElements.d.ts +2 -0
  195. package/lib/Utils/tabbableElements.d.ts.map +1 -0
  196. package/lib/Utils/tabbableElements.js +2 -2
  197. package/lib/connectToWebChat.js +17 -7
  198. package/lib/hooks/index.js +24 -24
  199. package/lib/hooks/internal/BypassSpeechSynthesisPonyfill.js +100 -41
  200. package/lib/hooks/internal/UITracker.js +2 -2
  201. package/lib/hooks/internal/useChanged.js +8 -1
  202. package/lib/hooks/internal/useDispatchScrollPosition.js +3 -7
  203. package/lib/hooks/internal/useDispatchTranscriptFocusByActivityKey.d.ts +2 -0
  204. package/lib/hooks/internal/useDispatchTranscriptFocusByActivityKey.d.ts.map +1 -0
  205. package/lib/hooks/internal/useDispatchTranscriptFocusByActivityKey.js +15 -0
  206. package/lib/hooks/internal/useEnterKeyHint.js +1 -1
  207. package/lib/hooks/internal/useFocusVisible.d.ts +3 -0
  208. package/lib/hooks/internal/useFocusVisible.d.ts.map +1 -0
  209. package/lib/hooks/internal/useFocusVisible.js +48 -0
  210. package/lib/hooks/internal/useForceRender.js +2 -2
  211. package/lib/hooks/internal/useForceRenderAtInterval.js +2 -2
  212. package/lib/hooks/internal/useInternalRenderMarkdownInline.js +1 -1
  213. package/lib/hooks/internal/useLocalizeAccessKey.js +2 -2
  214. package/lib/hooks/internal/useMemoWithPrevious.d.ts +3 -0
  215. package/lib/hooks/internal/useMemoWithPrevious.d.ts.map +1 -0
  216. package/lib/hooks/internal/useMemoWithPrevious.js +22 -0
  217. package/lib/hooks/internal/useMemoize.d.ts +14 -0
  218. package/lib/hooks/internal/useMemoize.d.ts.map +1 -0
  219. package/lib/hooks/internal/useMemoize.js +12 -3
  220. package/lib/hooks/internal/useNavigatorPlatform.js +1 -1
  221. package/lib/hooks/internal/useNonce.js +1 -1
  222. package/lib/hooks/internal/useObserveFocusVisible.d.ts +3 -0
  223. package/lib/hooks/internal/useObserveFocusVisible.d.ts.map +1 -0
  224. package/lib/hooks/internal/useObserveFocusVisible.js +208 -0
  225. package/lib/hooks/internal/usePrevious.d.ts +2 -0
  226. package/lib/hooks/internal/usePrevious.d.ts.map +1 -0
  227. package/lib/hooks/internal/usePrevious.js +18 -0
  228. package/lib/hooks/internal/useRegisterFocusSendBox.js +1 -1
  229. package/lib/hooks/internal/useRegisterFocusTranscript.js +1 -1
  230. package/lib/hooks/internal/useRegisterScrollRelative.js +1 -1
  231. package/lib/hooks/internal/useRegisterScrollTo.js +1 -1
  232. package/lib/hooks/internal/useRegisterScrollToEnd.js +1 -1
  233. package/lib/hooks/internal/useReplaceEmoticon.js +2 -2
  234. package/lib/hooks/internal/useResumeAudioContext.js +2 -2
  235. package/lib/hooks/internal/useScrollRelative.js +1 -1
  236. package/lib/hooks/internal/useSettableDictateAbortable.js +1 -1
  237. package/lib/hooks/internal/useStateRef.d.ts +3 -0
  238. package/lib/hooks/internal/useStateRef.d.ts.map +1 -0
  239. package/lib/hooks/internal/useStateRef.js +40 -0
  240. package/lib/hooks/internal/useSuggestedActionsAccessKey.js +1 -1
  241. package/lib/hooks/internal/useValueRef.d.ts +3 -0
  242. package/lib/hooks/internal/useValueRef.d.ts.map +1 -0
  243. package/lib/hooks/internal/useValueRef.js +25 -0
  244. package/lib/hooks/useDictateAbortable.js +2 -2
  245. package/lib/hooks/useFocus.d.ts +1 -1
  246. package/lib/hooks/useFocus.d.ts.map +1 -1
  247. package/lib/hooks/useFocus.js +1 -1
  248. package/lib/hooks/useObserveScrollPosition.js +2 -2
  249. package/lib/hooks/useObserveTranscriptFocus.js +2 -2
  250. package/lib/hooks/useRenderMarkdownAsHTML.d.ts.map +1 -1
  251. package/lib/hooks/useRenderMarkdownAsHTML.js +2 -2
  252. package/lib/hooks/useScrollTo.d.ts.map +1 -1
  253. package/lib/hooks/useScrollTo.js +1 -1
  254. package/lib/hooks/useScrollToEnd.d.ts.map +1 -1
  255. package/lib/hooks/useScrollToEnd.js +1 -1
  256. package/lib/hooks/useSendFiles.js +3 -3
  257. package/lib/index.d.ts +10 -0
  258. package/lib/index.d.ts.map +1 -1
  259. package/lib/index.js +20 -18
  260. package/lib/providers/ActivityTree/ActivityTreeComposer.d.ts +5 -0
  261. package/lib/providers/ActivityTree/ActivityTreeComposer.d.ts.map +1 -0
  262. package/lib/providers/ActivityTree/ActivityTreeComposer.js +86 -0
  263. package/lib/providers/ActivityTree/private/Context.d.ts +9 -0
  264. package/lib/providers/ActivityTree/private/Context.d.ts.map +1 -0
  265. package/lib/providers/ActivityTree/private/Context.js +13 -0
  266. package/lib/providers/ActivityTree/private/types.d.ts +10 -0
  267. package/lib/providers/ActivityTree/private/types.d.ts.map +1 -0
  268. package/lib/providers/ActivityTree/private/types.js +2 -0
  269. package/lib/providers/ActivityTree/private/useActivitiesWithRenderer.d.ts +4 -0
  270. package/lib/providers/ActivityTree/private/useActivitiesWithRenderer.d.ts.map +1 -0
  271. package/lib/providers/ActivityTree/private/useActivitiesWithRenderer.js +58 -0
  272. package/lib/providers/ActivityTree/private/useActivityTreeWithRenderer.d.ts +5 -0
  273. package/lib/providers/ActivityTree/private/useActivityTreeWithRenderer.d.ts.map +1 -0
  274. package/lib/providers/ActivityTree/private/useActivityTreeWithRenderer.js +166 -0
  275. package/lib/providers/ActivityTree/private/useContext.d.ts +3 -0
  276. package/lib/providers/ActivityTree/private/useContext.d.ts.map +1 -0
  277. package/lib/providers/ActivityTree/private/useContext.js +24 -0
  278. package/lib/providers/ActivityTree/useActivityTreeWithRenderer.d.ts +8 -0
  279. package/lib/providers/ActivityTree/useActivityTreeWithRenderer.d.ts.map +1 -0
  280. package/lib/providers/ActivityTree/useActivityTreeWithRenderer.js +17 -0
  281. package/lib/providers/LiveRegionTwin/LiveRegionTwinComposer.d.ts +35 -0
  282. package/lib/providers/LiveRegionTwin/LiveRegionTwinComposer.d.ts.map +1 -0
  283. package/lib/providers/LiveRegionTwin/LiveRegionTwinComposer.js +156 -0
  284. package/lib/providers/LiveRegionTwin/private/Context.d.ts +10 -0
  285. package/lib/providers/LiveRegionTwin/private/Context.d.ts.map +1 -0
  286. package/lib/providers/LiveRegionTwin/private/Context.js +13 -0
  287. package/lib/providers/LiveRegionTwin/private/LiveRegionTwinContainer.d.ts +11 -0
  288. package/lib/providers/LiveRegionTwin/private/LiveRegionTwinContainer.d.ts.map +1 -0
  289. package/lib/providers/LiveRegionTwin/private/LiveRegionTwinContainer.js +86 -0
  290. package/lib/providers/LiveRegionTwin/private/types.d.ts +8 -0
  291. package/lib/providers/LiveRegionTwin/private/types.d.ts.map +1 -0
  292. package/lib/providers/LiveRegionTwin/private/types.js +2 -0
  293. package/lib/providers/LiveRegionTwin/private/useContext.d.ts +3 -0
  294. package/lib/providers/LiveRegionTwin/private/useContext.d.ts.map +1 -0
  295. package/lib/providers/LiveRegionTwin/private/useContext.js +24 -0
  296. package/lib/providers/LiveRegionTwin/private/useMarkAllAsRenderedEffect.d.ts +2 -0
  297. package/lib/providers/LiveRegionTwin/private/useMarkAllAsRenderedEffect.d.ts.map +1 -0
  298. package/lib/providers/LiveRegionTwin/private/useMarkAllAsRenderedEffect.js +24 -0
  299. package/lib/providers/LiveRegionTwin/private/useStaticElementEntries.d.ts +3 -0
  300. package/lib/providers/LiveRegionTwin/private/useStaticElementEntries.d.ts.map +1 -0
  301. package/lib/providers/LiveRegionTwin/private/useStaticElementEntries.js +15 -0
  302. package/lib/providers/LiveRegionTwin/useQueueStaticElement.d.ts +8 -0
  303. package/lib/providers/LiveRegionTwin/useQueueStaticElement.d.ts.map +1 -0
  304. package/lib/providers/LiveRegionTwin/useQueueStaticElement.js +20 -0
  305. package/lib/providers/TranscriptFocus/TranscriptFocusComposer.d.ts +7 -0
  306. package/lib/providers/TranscriptFocus/TranscriptFocusComposer.d.ts.map +1 -0
  307. package/lib/providers/TranscriptFocus/TranscriptFocusComposer.js +184 -0
  308. package/lib/providers/TranscriptFocus/private/Context.d.ts +12 -0
  309. package/lib/providers/TranscriptFocus/private/Context.d.ts.map +1 -0
  310. package/lib/providers/TranscriptFocus/private/Context.js +13 -0
  311. package/lib/providers/TranscriptFocus/private/useContext.d.ts +2 -0
  312. package/lib/providers/TranscriptFocus/private/useContext.d.ts.map +1 -0
  313. package/lib/providers/TranscriptFocus/private/useContext.js +24 -0
  314. package/lib/providers/TranscriptFocus/useActiveDescendantId.d.ts +2 -0
  315. package/lib/providers/TranscriptFocus/useActiveDescendantId.d.ts.map +1 -0
  316. package/lib/providers/TranscriptFocus/useActiveDescendantId.js +15 -0
  317. package/lib/providers/TranscriptFocus/useFocusByActivityKey.d.ts +8 -0
  318. package/lib/providers/TranscriptFocus/useFocusByActivityKey.d.ts.map +1 -0
  319. package/lib/providers/TranscriptFocus/useFocusByActivityKey.js +21 -0
  320. package/lib/providers/TranscriptFocus/useFocusRelativeActivity.d.ts +2 -0
  321. package/lib/providers/TranscriptFocus/useFocusRelativeActivity.d.ts.map +1 -0
  322. package/lib/providers/TranscriptFocus/useFocusRelativeActivity.js +15 -0
  323. package/lib/providers/TranscriptFocus/useFocusedActivityKey.d.ts +2 -0
  324. package/lib/providers/TranscriptFocus/useFocusedActivityKey.d.ts.map +1 -0
  325. package/lib/providers/TranscriptFocus/useFocusedActivityKey.js +15 -0
  326. package/lib/providers/TranscriptFocus/useFocusedExplicitly.d.ts +2 -0
  327. package/lib/providers/TranscriptFocus/useFocusedExplicitly.d.ts.map +1 -0
  328. package/lib/providers/TranscriptFocus/useFocusedExplicitly.js +15 -0
  329. package/lib/providers/TranscriptFocus/useGetDescendantIdByActivityKey.d.ts +2 -0
  330. package/lib/providers/TranscriptFocus/useGetDescendantIdByActivityKey.d.ts.map +1 -0
  331. package/lib/providers/TranscriptFocus/useGetDescendantIdByActivityKey.js +15 -0
  332. package/package.json +25 -33
  333. package/src/Activity/CarouselFilmStrip.js +2 -3
  334. package/src/Activity/CarouselFilmStripAttachment.js +0 -1
  335. package/src/Activity/StackedLayout.tsx +10 -9
  336. package/src/Attachment/FileAttachment.js +1 -1
  337. package/src/Attachment/FileContent.tsx +12 -0
  338. package/src/BasicToaster.js +9 -5
  339. package/src/BasicTranscript.tsx +898 -0
  340. package/src/BasicTypingIndicator.tsx +3 -2
  341. package/src/Composer.tsx +41 -29
  342. package/src/Dictation.js +4 -3
  343. package/src/Middleware/Activity/createCoreMiddleware.tsx +50 -44
  344. package/src/Middleware/ActivityStatus/createSendStatusMiddleware.js +10 -6
  345. package/src/Middleware/ActivityStatus/createTimestampMiddleware.js +10 -8
  346. package/src/Middleware/Attachment/createCoreMiddleware.tsx +28 -28
  347. package/src/Middleware/AttachmentForScreenReader/createCoreMiddleware.tsx +25 -23
  348. package/src/Middleware/Avatar/createCoreMiddleware.tsx +9 -8
  349. package/src/Middleware/CardAction/createCoreMiddleware.js +50 -41
  350. package/src/Middleware/GroupActivities/createCoreMiddleware.js +6 -4
  351. package/src/Middleware/ScrollToEndButton/createScrollToEndButtonMiddleware.ts +11 -9
  352. package/src/Middleware/Toast/createCoreMiddleware.tsx +12 -10
  353. package/src/Middleware/TypingIndicator/createCoreMiddleware.tsx +8 -2
  354. package/src/ScreenReaderActivity.js +20 -6
  355. package/src/{ScreenReaderText.js → ScreenReaderText.tsx} +27 -9
  356. package/src/SendBox/{IconButton.js → IconButton.tsx} +19 -3
  357. package/src/SendBox/{SuggestedAction.js → SuggestedAction.tsx} +72 -35
  358. package/src/SendBox/SuggestedActions.tsx +64 -21
  359. package/src/Styles/StyleSet/BasicTranscript.ts +34 -20
  360. package/src/Styles/StyleSet/Bubble.ts +0 -1
  361. package/src/Styles/StyleSet/CarouselFilmStrip.ts +12 -10
  362. package/src/Styles/StyleSet/CarouselFilmStripAttachment.ts +4 -3
  363. package/src/Styles/StyleSet/KeyboardHelp.ts +157 -0
  364. package/src/Styles/StyleSet/ScrollToEndButton.ts +1 -1
  365. package/src/Styles/StyleSet/SendBoxButton.ts +84 -13
  366. package/src/Styles/StyleSet/SendBoxTextBox.ts +1 -2
  367. package/src/Styles/StyleSet/StackedLayout.ts +13 -11
  368. package/src/Styles/StyleSet/SuggestedAction.ts +129 -42
  369. package/src/Styles/StyleSet/SuggestedActions.ts +13 -5
  370. package/src/Styles/createStyleSet.ts +2 -1
  371. package/src/Styles/mirrorStyle.js +10 -2
  372. package/src/Toast/NotificationIcon.js +4 -1
  373. package/src/Toast/createToastMiddleware.tsx +4 -1
  374. package/src/Transcript/ActivityRow.tsx +124 -0
  375. package/src/Transcript/ActivityTextAlt.tsx +32 -0
  376. package/src/Transcript/FocusTrap.tsx +64 -0
  377. package/src/Transcript/KeyboardHelp.tsx +282 -0
  378. package/src/Transcript/LiveRegionTranscript.tsx +181 -0
  379. package/src/Transcript/types.ts +1 -0
  380. package/src/Transcript/useActivityAccessibleName.ts +85 -0
  381. package/src/Utils/{AccessibleButton.js → AccessibleButton.tsx} +19 -4
  382. package/src/Utils/{FocusRedirector.js → FocusRedirector.tsx} +21 -8
  383. package/src/Utils/InlineMarkdown.js +18 -2
  384. package/src/Utils/TypeFocusSink/FocusBox.js +4 -4
  385. package/src/Utils/TypeFocusSink/inputtableKey.ts +5 -1
  386. package/src/Utils/createCustomEvent.js +7 -1
  387. package/src/Utils/detectBrowser.js +2 -1
  388. package/src/Utils/findAncestor.ts +12 -0
  389. package/src/Utils/getActivityUniqueId.ts +5 -0
  390. package/src/Utils/intersectionOf.ts +14 -0
  391. package/src/Utils/isZeroOrPositive.ts +7 -0
  392. package/src/Utils/mapMap.js +7 -1
  393. package/src/Utils/scrollIntoViewWithBlockNearest.ts +20 -0
  394. package/src/Utils/shallowEquals.js +8 -1
  395. package/src/Utils/supportPseudoClass.ts +17 -0
  396. package/src/Utils/{tabbableElements.js → tabbableElements.ts} +6 -5
  397. package/src/connectToWebChat.js +11 -4
  398. package/src/hooks/internal/BypassSpeechSynthesisPonyfill.js +70 -17
  399. package/src/hooks/internal/useChanged.ts +17 -0
  400. package/src/hooks/internal/useDispatchScrollPosition.js +1 -3
  401. package/src/hooks/internal/useDispatchTranscriptFocusByActivityKey.ts +5 -0
  402. package/src/hooks/internal/useFocusVisible.ts +22 -0
  403. package/src/hooks/internal/useMemoWithPrevious.ts +16 -0
  404. package/src/hooks/internal/useMemoize.spec.js +1 -1
  405. package/src/hooks/internal/useMemoize.ts +53 -0
  406. package/src/hooks/internal/useObserveFocusVisible.ts +252 -0
  407. package/src/hooks/internal/usePrevious.ts +12 -0
  408. package/src/hooks/internal/useScrollRelative.js +4 -3
  409. package/src/hooks/internal/useStateRef.ts +31 -0
  410. package/src/hooks/internal/useValueRef.ts +22 -0
  411. package/src/hooks/useFocus.ts +1 -1
  412. package/src/hooks/useRenderMarkdownAsHTML.ts +4 -5
  413. package/src/hooks/useScrollTo.ts +4 -3
  414. package/src/hooks/useScrollToEnd.ts +4 -3
  415. package/src/index.ts +0 -1
  416. package/src/providers/ActivityTree/ActivityTreeComposer.tsx +74 -0
  417. package/src/providers/ActivityTree/private/Context.ts +12 -0
  418. package/src/providers/ActivityTree/private/types.ts +12 -0
  419. package/src/providers/ActivityTree/private/useActivitiesWithRenderer.ts +66 -0
  420. package/src/providers/ActivityTree/private/useActivityTreeWithRenderer.ts +140 -0
  421. package/src/providers/ActivityTree/private/useContext.ts +15 -0
  422. package/src/providers/ActivityTree/useActivityTreeWithRenderer.ts +16 -0
  423. package/src/providers/LiveRegionTwin/LiveRegionTwinComposer.tsx +154 -0
  424. package/src/providers/LiveRegionTwin/private/Context.ts +15 -0
  425. package/src/providers/LiveRegionTwin/private/LiveRegionTwinContainer.tsx +64 -0
  426. package/src/providers/LiveRegionTwin/private/types.ts +10 -0
  427. package/src/providers/LiveRegionTwin/private/useContext.ts +15 -0
  428. package/src/providers/LiveRegionTwin/private/useMarkAllAsRenderedEffect.ts +13 -0
  429. package/src/providers/LiveRegionTwin/private/useStaticElementEntries.ts +7 -0
  430. package/src/providers/LiveRegionTwin/useQueueStaticElement.ts +12 -0
  431. package/src/providers/TranscriptFocus/TranscriptFocusComposer.tsx +180 -0
  432. package/src/providers/TranscriptFocus/private/Context.ts +16 -0
  433. package/src/providers/TranscriptFocus/private/useContext.ts +13 -0
  434. package/src/providers/TranscriptFocus/useActiveDescendantId.ts +5 -0
  435. package/src/providers/TranscriptFocus/useFocusByActivityKey.ts +14 -0
  436. package/src/providers/TranscriptFocus/useFocusRelativeActivity.ts +5 -0
  437. package/src/providers/TranscriptFocus/useFocusedActivityKey.ts +5 -0
  438. package/src/providers/TranscriptFocus/useFocusedExplicitly.ts +5 -0
  439. package/src/providers/TranscriptFocus/useGetDescendantIdByActivityKey.ts +5 -0
  440. package/.eslintignore +0 -1
  441. package/lib/Utils/findLastIndex.js +0 -32
  442. package/lib/hooks/internal/useAcknowledgedActivity.js +0 -90
  443. package/lib/hooks/internal/useDispatchTranscriptFocus.js +0 -19
  444. package/src/BasicTranscript.js +0 -1140
  445. package/src/Utils/findLastIndex.js +0 -11
  446. package/src/Utils/findLastIndex.spec.js +0 -31
  447. package/src/Utils/getActivityUniqueId.js +0 -3
  448. package/src/Utils/intersectionOf.js +0 -11
  449. package/src/Utils/isZeroOrPositive.js +0 -4
  450. package/src/hooks/internal/useAcknowledgedActivity.js +0 -65
  451. package/src/hooks/internal/useChanged.js +0 -10
  452. package/src/hooks/internal/useDispatchTranscriptFocus.js +0 -7
  453. package/src/hooks/internal/useMemoize.js +0 -37
@@ -6,11 +6,12 @@
6
6
  /* eslint max-classes-per-file: ["error", 4] */
7
7
  /* eslint no-empty-function: "off" */
8
8
 
9
- import EventTarget, { defineEventAttribute } from 'event-target-shim-es5';
9
+ import EventTarget, { Event, getEventAttributeValue, setEventAttributeValue } from 'event-target-shim/es5';
10
10
 
11
- class SpeechSynthesisEvent {
11
+ class SpeechSynthesisEvent extends Event {
12
12
  constructor(type, utterance) {
13
- this._type = type;
13
+ super(type);
14
+
14
15
  this._utterance = utterance;
15
16
  }
16
17
 
@@ -22,10 +23,8 @@ class SpeechSynthesisEvent {
22
23
  return 0;
23
24
  }
24
25
 
25
- get name() {}
26
-
27
- get type() {
28
- return this._type;
26
+ get name() {
27
+ // It is expected to return `undefined`, keeping the function empty to reduce footprint.
29
28
  }
30
29
 
31
30
  get utterance() {
@@ -92,15 +91,63 @@ class SpeechSynthesisUtterance extends EventTarget {
92
91
  set volume(value) {
93
92
  this._volume = value;
94
93
  }
95
- }
96
94
 
97
- defineEventAttribute(SpeechSynthesisUtterance.prototype, 'boundary');
98
- defineEventAttribute(SpeechSynthesisUtterance.prototype, 'end');
99
- defineEventAttribute(SpeechSynthesisUtterance.prototype, 'error');
100
- defineEventAttribute(SpeechSynthesisUtterance.prototype, 'mark');
101
- defineEventAttribute(SpeechSynthesisUtterance.prototype, 'pause');
102
- defineEventAttribute(SpeechSynthesisUtterance.prototype, 'resume');
103
- defineEventAttribute(SpeechSynthesisUtterance.prototype, 'start');
95
+ get onboundary() {
96
+ return getEventAttributeValue(this, 'boundary');
97
+ }
98
+
99
+ set onboundary(value) {
100
+ setEventAttributeValue(this, 'boundary', value);
101
+ }
102
+
103
+ get onend() {
104
+ return getEventAttributeValue(this, 'end');
105
+ }
106
+
107
+ set onend(value) {
108
+ setEventAttributeValue(this, 'end', value);
109
+ }
110
+
111
+ get onerror() {
112
+ return getEventAttributeValue(this, 'error');
113
+ }
114
+
115
+ set onerror(value) {
116
+ setEventAttributeValue(this, 'error', value);
117
+ }
118
+
119
+ get onmark() {
120
+ return getEventAttributeValue(this, 'mark');
121
+ }
122
+
123
+ set onmark(value) {
124
+ setEventAttributeValue(this, 'mark', value);
125
+ }
126
+
127
+ get onpause() {
128
+ return getEventAttributeValue(this, 'pause');
129
+ }
130
+
131
+ set onpause(value) {
132
+ setEventAttributeValue(this, 'pause', value);
133
+ }
134
+
135
+ get onresume() {
136
+ return getEventAttributeValue(this, 'resume');
137
+ }
138
+
139
+ set onresume(value) {
140
+ setEventAttributeValue(this, 'resume', value);
141
+ }
142
+
143
+ get onstart() {
144
+ return getEventAttributeValue(this, 'start');
145
+ }
146
+
147
+ set onstart(value) {
148
+ setEventAttributeValue(this, 'start', value);
149
+ }
150
+ }
104
151
 
105
152
  class SpeechSynthesisVoice {
106
153
  get default() {
@@ -155,9 +202,15 @@ class SpeechSynthesis extends EventTarget {
155
202
  utterance.dispatchEvent(new SpeechSynthesisEvent('start', utterance));
156
203
  utterance.dispatchEvent(new SpeechSynthesisEvent('end', utterance));
157
204
  }
158
- }
159
205
 
160
- defineEventAttribute(SpeechSynthesis.prototype, 'voiceschanged');
206
+ get onvoiceschanged() {
207
+ return getEventAttributeValue(this, 'voiceschanged');
208
+ }
209
+
210
+ set onvoiceschanged(value) {
211
+ setEventAttributeValue(this, 'voiceschanged', value);
212
+ }
213
+ }
161
214
 
162
215
  const speechSynthesis = new SpeechSynthesis();
163
216
 
@@ -0,0 +1,17 @@
1
+ import { useRef } from 'react';
2
+
3
+ /**
4
+ * Returns `true` if the `value` has changed, otherwise, `false`.
5
+ *
6
+ * Note: on initial call, this will return `true`.
7
+ *
8
+ * @param {T} value - The `value` to detect for changes.
9
+ */
10
+ export default function useChanged<T>(value: T): boolean {
11
+ const prevValueRef = useRef(value);
12
+ const changed = value !== prevValueRef.current;
13
+
14
+ prevValueRef.current = value;
15
+
16
+ return changed;
17
+ }
@@ -1,7 +1,5 @@
1
1
  import useWebChatUIContext from './useWebChatUIContext';
2
2
 
3
3
  export default function useDispatchScrollPosition() {
4
- const { dispatchScrollPosition, numScrollPositionObservers } = useWebChatUIContext();
5
-
6
- return numScrollPositionObservers ? dispatchScrollPosition : undefined;
4
+ return useWebChatUIContext().dispatchScrollPosition;
7
5
  }
@@ -0,0 +1,5 @@
1
+ import useWebChatUIContext from './useWebChatUIContext';
2
+
3
+ export default function useDispatchTranscriptFocusByActivityKey(): (activityKey: string | undefined) => void {
4
+ return useWebChatUIContext().dispatchTranscriptFocusByActivityKey;
5
+ }
@@ -0,0 +1,22 @@
1
+ import { RefObject, useCallback, useEffect, useState } from 'react';
2
+
3
+ import useObserveFocusVisible from './useObserveFocusVisible';
4
+
5
+ export default function useFocusVisible(targetRef: RefObject<HTMLElement>): [boolean] {
6
+ const [focusVisible, setFocusVisible] = useState(false);
7
+
8
+ const handleBlur = useCallback(() => setFocusVisible(false), [setFocusVisible]);
9
+ const handleFocusVisible = useCallback(() => setFocusVisible(true), [setFocusVisible]);
10
+
11
+ useObserveFocusVisible(targetRef, handleFocusVisible);
12
+
13
+ useEffect(() => {
14
+ const { current } = targetRef;
15
+
16
+ current.addEventListener('blur', handleBlur);
17
+
18
+ return () => current.removeEventListener('blur', handleBlur);
19
+ }, [handleBlur, targetRef]);
20
+
21
+ return [focusVisible];
22
+ }
@@ -0,0 +1,16 @@
1
+ import { useEffect, useMemo, useRef } from 'react';
2
+
3
+ import type { DependencyList } from 'react';
4
+
5
+ export default function useMemoWithPrevious<T>(factory: (prevValue: T) => T, deps: DependencyList): T {
6
+ const prevValueRef = useRef<T>();
7
+ // We are building a `useMemo`-like hook, `deps` is passed as-is and `factory` is not one fo the dependencies.
8
+ // eslint-disable-next-line react-hooks/exhaustive-deps
9
+ const value = useMemo<T>(() => factory(prevValueRef.current), deps);
10
+
11
+ useEffect(() => {
12
+ prevValueRef.current = value;
13
+ });
14
+
15
+ return value;
16
+ }
@@ -7,7 +7,7 @@ jest.mock('react', () => {
7
7
  let lastResult;
8
8
 
9
9
  function arrayEquals(x, y) {
10
- return x.length === y.length && x.every((item, index) => Object.is(item, y[index]));
10
+ return x.length === y.length && [].every.call(x, (item, index) => Object.is(item, y[+index]));
11
11
  }
12
12
 
13
13
  return {
@@ -0,0 +1,53 @@
1
+ import { DependencyList, useMemo } from 'react';
2
+
3
+ type Cache<TArgs, TResult> = { args: TArgs[]; result: TResult };
4
+ type Fn<TArgs, TResult> = (...args: TArgs[]) => TResult;
5
+
6
+ /**
7
+ * `useMemoize` will memoize multiple calls to the same memoize function.
8
+ *
9
+ * This is similar to `useMemo`. But instead of calling it once, `useMemoize` enables multiple calls while the `callback` function is executed.
10
+ *
11
+ * @param {Fn<TArgs, TIntermediate>} fn - The function to be memoized.
12
+ * @param {(fn: Fn<TArgs, TIntermediate>) => TFinal} callback - When called, this function should execute the memoizing function.
13
+ * @param {DependencyList[]} deps - Dependencies to detect for chagnes.
14
+ */
15
+ export default function useMemoize<TArgs extends [], TIntermediate, TFinal>(
16
+ fn: Fn<TArgs, TIntermediate>,
17
+ callback: (fn: Fn<TArgs, TIntermediate>) => TFinal,
18
+ deps: DependencyList[]
19
+ ): TFinal {
20
+ if (typeof fn !== 'function') {
21
+ throw new Error('The first argument must be a function.');
22
+ } else if (typeof callback !== 'function') {
23
+ throw new Error('The second argument must be a function.');
24
+ } else if (!Array.isArray(deps)) {
25
+ throw new Error('The third argument must be an array.');
26
+ }
27
+
28
+ const memoizedFn = useMemo(() => {
29
+ let cache: Cache<TArgs, TIntermediate>[] = [];
30
+
31
+ return (run: (fn: Fn<TArgs, TIntermediate>) => TFinal) => {
32
+ const nextCache: Cache<TArgs, TIntermediate>[] = [];
33
+ const result = run((...args) => {
34
+ const { result } = [...cache, ...nextCache].find(
35
+ ({ args: cachedArgs }) =>
36
+ args.length === cachedArgs.length && args.every((arg, index) => Object.is(arg, cachedArgs[+index]))
37
+ ) || { result: fn(...args) };
38
+
39
+ nextCache.push({ args, result });
40
+
41
+ return result;
42
+ });
43
+
44
+ cache = nextCache;
45
+
46
+ return result;
47
+ };
48
+ // We are manually creating the deps here. The "callback" arg is also designed not to be impact deps, similar to useEffect(fn), where "fn" is not in deps.
49
+ /* eslint-disable-next-line react-hooks/exhaustive-deps */
50
+ }, [fn, ...deps]);
51
+
52
+ return memoizedFn(callback);
53
+ }
@@ -0,0 +1,252 @@
1
+ import { MutableRefObject, RefObject, useCallback, useEffect, useMemo, useRef } from 'react';
2
+
3
+ import supportPseudoClass from '../../Utils/supportPseudoClass';
4
+ import useNonce from './useNonce';
5
+ import useValueRef from './useValueRef';
6
+
7
+ const INPUT_TYPES_ALLOW_LIST = [
8
+ 'date',
9
+ 'datetime-local',
10
+ 'datetime',
11
+ 'email',
12
+ 'month',
13
+ 'number',
14
+ 'password',
15
+ 'search',
16
+ 'tel',
17
+ 'text',
18
+ 'time',
19
+ 'url',
20
+ 'week'
21
+ ];
22
+
23
+ /**
24
+ * Computes whether the given element should automatically trigger the
25
+ * `focus-visible` class being added, i.e. whether it should always match
26
+ * `:focus-visible` when focused.
27
+ * @param {Element} el
28
+ * @return {boolean}
29
+ */
30
+ function focusTriggersKeyboardModality(el: HTMLInputElement | HTMLTextAreaElement): boolean {
31
+ const { isContentEditable, readOnly, tagName, type } = el;
32
+
33
+ return (
34
+ (tagName === 'INPUT' && INPUT_TYPES_ALLOW_LIST.includes(type) && !readOnly) ||
35
+ (tagName === 'TEXTAREA' && !readOnly) ||
36
+ isContentEditable
37
+ );
38
+ }
39
+
40
+ function createEventSubscription(
41
+ target: Element | Node,
42
+ types: string[],
43
+ handler: (event: Event) => void
44
+ ): {
45
+ pause: () => void;
46
+ resume: () => void;
47
+ } {
48
+ let subscribed: true;
49
+
50
+ const subscribe = () => {
51
+ if (!subscribed) {
52
+ types.forEach(type => target.addEventListener(type, handler));
53
+ subscribed = true;
54
+ }
55
+ };
56
+
57
+ const unsubscribe = () => {
58
+ if (subscribed) {
59
+ types.forEach(type => target.removeEventListener(type, handler));
60
+ subscribed = undefined;
61
+ }
62
+ };
63
+
64
+ return {
65
+ pause: unsubscribe,
66
+ resume: subscribe
67
+ };
68
+ }
69
+
70
+ // TODO: Add tests
71
+ // 1. Focus via keyboard vs. mouse
72
+ // 2. Focus via keyboard, switch app, switch back (expect to get another focusVisible after switch back)
73
+ // 3. Focus via mouse, switch app, switch back (do NOT expect to get another focusVisible after switch back)
74
+ function useObserveFocusVisibleForLegacyBrowsers(
75
+ targetRef: RefObject<HTMLElement>,
76
+ onFocusVisibleRef: MutableRefObject<() => void>
77
+ ) {
78
+ // This polyfill algorithm is adopted from https://github.com/WICG/focus-visible.
79
+ const blurSinceRef = useRef(0);
80
+ const hadKeyboardEventRef = useRef(true);
81
+ const hasFocusVisibleRef = useRef(false);
82
+
83
+ const eventSubscription = useMemo(
84
+ () =>
85
+ createEventSubscription(
86
+ document,
87
+ [
88
+ 'mousemove',
89
+ 'mousedown',
90
+ 'mouseup',
91
+ 'pointermove',
92
+ 'pointerdown',
93
+ 'pointerup',
94
+ 'touchmove',
95
+ 'touchstart',
96
+ 'touchend'
97
+ ],
98
+ event => {
99
+ if ((event.target as HTMLElement).nodeName?.toLowerCase() !== 'html') {
100
+ hadKeyboardEventRef.current = false;
101
+ eventSubscription.pause();
102
+ }
103
+ }
104
+ ),
105
+ [hadKeyboardEventRef]
106
+ );
107
+
108
+ const setHasFocusVisible = useCallback(
109
+ nextHasFocusVisible => {
110
+ if (hasFocusVisibleRef.current !== nextHasFocusVisible) {
111
+ hasFocusVisibleRef.current = nextHasFocusVisible;
112
+ nextHasFocusVisible && onFocusVisibleRef?.current();
113
+ }
114
+ },
115
+ [hasFocusVisibleRef, onFocusVisibleRef]
116
+ );
117
+
118
+ const handleKeyDown = useCallback(
119
+ (event: KeyboardEvent) => {
120
+ if (event.altKey || event.ctrlKey || event.metaKey) {
121
+ return;
122
+ }
123
+
124
+ if (event.target === targetRef.current) {
125
+ setHasFocusVisible(true);
126
+ }
127
+
128
+ hadKeyboardEventRef.current = true;
129
+ },
130
+ [hadKeyboardEventRef, setHasFocusVisible, targetRef]
131
+ );
132
+
133
+ const handlePointerDown = useCallback(() => {
134
+ hadKeyboardEventRef.current = false;
135
+ }, [hadKeyboardEventRef]);
136
+
137
+ const handleFocus = useCallback(
138
+ ({ target }: Event) => {
139
+ target === targetRef.current &&
140
+ (hadKeyboardEventRef.current || focusTriggersKeyboardModality(target as HTMLInputElement)) &&
141
+ setHasFocusVisible(true);
142
+ },
143
+ [hadKeyboardEventRef, setHasFocusVisible, targetRef]
144
+ );
145
+
146
+ const handleBlur = useCallback(
147
+ (event: Event) => {
148
+ if (event.target === targetRef.current && hasFocusVisibleRef.current) {
149
+ blurSinceRef.current = Date.now();
150
+
151
+ setHasFocusVisible(false);
152
+ }
153
+ },
154
+ [blurSinceRef, hasFocusVisibleRef, setHasFocusVisible, targetRef]
155
+ );
156
+
157
+ const handleVisibilityChange = useCallback(() => {
158
+ if (document.visibilityState === 'hidden') {
159
+ // The element is blurred due to "visibilityState" set to "hidden".
160
+ // 100ms is referenced from the WICG polyfill.
161
+ // eslint-disable-next-line no-magic-numbers
162
+ if (Date.now() - blurSinceRef.current < 100) {
163
+ hadKeyboardEventRef.current = true;
164
+ }
165
+
166
+ eventSubscription.resume();
167
+ }
168
+ }, [blurSinceRef, eventSubscription, hadKeyboardEventRef]);
169
+
170
+ useEffect(() => {
171
+ document.addEventListener('keydown', handleKeyDown, true);
172
+ document.addEventListener('mousedown', handlePointerDown, true);
173
+ document.addEventListener('pointerdown', handlePointerDown, true);
174
+ document.addEventListener('touchstart', handlePointerDown, true);
175
+ document.addEventListener('visibilitychange', handleVisibilityChange, true);
176
+
177
+ return () => {
178
+ document.removeEventListener('keydown', handleKeyDown);
179
+ document.removeEventListener('mousedown', handlePointerDown);
180
+ document.removeEventListener('pointerdown', handlePointerDown);
181
+ document.removeEventListener('touchstart', handlePointerDown);
182
+ document.removeEventListener('visibilitychange', handleVisibilityChange);
183
+ };
184
+ }, [handleKeyDown, handlePointerDown, handleVisibilityChange]);
185
+
186
+ useEffect(() => {
187
+ const { current: target } = targetRef;
188
+
189
+ target.addEventListener('blur', handleBlur, true);
190
+ target.addEventListener('focus', handleFocus, true);
191
+
192
+ return () => {
193
+ target.removeEventListener('blur', handleBlur);
194
+ target.removeEventListener('focus', handleFocus);
195
+ };
196
+
197
+ // We specifically add "targetRef.current" here.
198
+ // If the target element changed, we should reattach our event listeners.
199
+ }, [handleBlur, handleFocus, targetRef]);
200
+
201
+ useEffect(() => {
202
+ eventSubscription.resume();
203
+
204
+ return () => eventSubscription.pause();
205
+ }, [eventSubscription]);
206
+ }
207
+
208
+ function useObserveFocusVisibleForModernBrowsers(
209
+ targetRef: RefObject<HTMLElement>,
210
+ onFocusVisibleRef: MutableRefObject<() => void>
211
+ ) {
212
+ const handleFocus = useCallback(() => {
213
+ if (targetRef.current.matches(':focus-visible')) {
214
+ onFocusVisibleRef?.current();
215
+ }
216
+ }, [onFocusVisibleRef, targetRef]);
217
+
218
+ useEffect(() => {
219
+ const { current: target } = targetRef;
220
+
221
+ target.addEventListener('focus', handleFocus);
222
+
223
+ return () => target.removeEventListener('focus', handleFocus);
224
+
225
+ // We specifically add "targetRef.current" here.
226
+ // If the target element changed, we should reattach our event listeners.
227
+ // eslint-disable-next-line react-hooks/exhaustive-deps
228
+ }, [handleFocus, targetRef, targetRef.current]);
229
+ }
230
+
231
+ export default function useObserveFocusVisible(targetRef: RefObject<HTMLElement>, onFocusVisible: () => void) {
232
+ const [nonce] = useNonce();
233
+ const onFocusVisibleRef = useValueRef(onFocusVisible);
234
+
235
+ // The nonce is use for browser capabilities. Just in case the "nonce" had changed unexpectedly, the capabilities of the browser should never change.
236
+ // Thus, we are using an initial version of "nonce". In case web devs changed the "nonce" to an invalid value, we won't break rules of hooks (as stated below).
237
+ const nonceRef = useRef(nonce);
238
+
239
+ // ":focus-visible" selector is supported from Chrome/Edge 86+ and not supported in IE11 or Safari.
240
+ // Doing a capability check on pseudo classes requires injecting a stylesheet, thus nonce is needed.
241
+ const supportFocusVisible = useMemo(() => supportPseudoClass(':focus-visible', nonceRef.current), [nonceRef]);
242
+
243
+ // Since "supportPseudoClass" is a browser capability, the result should be constant during the page lifetime.
244
+ // Thus, running hooks conditionally is okay here.
245
+ if (supportFocusVisible) {
246
+ // eslint-disable-next-line react-hooks/rules-of-hooks
247
+ useObserveFocusVisibleForModernBrowsers(targetRef, onFocusVisibleRef);
248
+ } else {
249
+ // eslint-disable-next-line react-hooks/rules-of-hooks
250
+ useObserveFocusVisibleForLegacyBrowsers(targetRef, onFocusVisibleRef);
251
+ }
252
+ }
@@ -0,0 +1,12 @@
1
+ // TODO: [P0] #4133 Don't copy.
2
+ import { useEffect, useRef } from 'react';
3
+
4
+ export default function usePrevious<T>(value: T): T {
5
+ const ref = useRef<T>();
6
+
7
+ useEffect(() => {
8
+ ref.current = value;
9
+ });
10
+
11
+ return ref.current;
12
+ }
@@ -5,7 +5,8 @@ import useWebChatUIContext from './useWebChatUIContext';
5
5
  export default function useScrollRelative() {
6
6
  const { scrollRelativeCallbacksRef } = useWebChatUIContext();
7
7
 
8
- return useCallback((...args) => scrollRelativeCallbacksRef.current.forEach(callback => callback(...args)), [
9
- scrollRelativeCallbacksRef
10
- ]);
8
+ return useCallback(
9
+ (...args) => scrollRelativeCallbacksRef.current.forEach(callback => callback(...args)),
10
+ [scrollRelativeCallbacksRef]
11
+ );
11
12
  }
@@ -0,0 +1,31 @@
1
+ import { useCallback, useRef, useState } from 'react';
2
+
3
+ import type { Dispatch, MutableRefObject, SetStateAction } from 'react';
4
+
5
+ export default function useStateRef<T>(
6
+ initialValue?: T
7
+ ): readonly [T, Dispatch<SetStateAction<T>>, MutableRefObject<T>] {
8
+ const [_, forceRender] = useState<{}>();
9
+ const valueRef: MutableRefObject<T> = useRef<T>(initialValue);
10
+
11
+ const setter: Dispatch<SetStateAction<T>> = useCallback(
12
+ (value: SetStateAction<T>) => {
13
+ const { current } = valueRef;
14
+
15
+ value = value instanceof Function ? value(current) : value;
16
+
17
+ if (current !== value) {
18
+ valueRef.current = value;
19
+
20
+ forceRender({});
21
+ }
22
+ },
23
+ [forceRender, valueRef]
24
+ );
25
+
26
+ return Object.freeze([valueRef.current, setter, valueRef]) as readonly [
27
+ T,
28
+ Dispatch<SetStateAction<T>>,
29
+ MutableRefObject<T>
30
+ ];
31
+ }
@@ -0,0 +1,22 @@
1
+ // TODO: [P0] #4133 Don't copy.
2
+ import { RefObject, useMemo, useRef } from 'react';
3
+
4
+ export default function useValueRef<T>(value: T): RefObject<T> {
5
+ const ref = useRef<T>();
6
+ const readOnlyRef = useMemo(
7
+ () =>
8
+ Object.create(
9
+ {},
10
+ {
11
+ current: {
12
+ get: () => ref.current
13
+ }
14
+ }
15
+ ),
16
+ []
17
+ );
18
+
19
+ ref.current = value;
20
+
21
+ return readOnlyRef;
22
+ }
@@ -2,7 +2,7 @@ import { useCallback } from 'react';
2
2
 
3
3
  import useWebChatUIContext from './internal/useWebChatUIContext';
4
4
 
5
- export default function useFocus(): (where?: 'sendBox' | 'sendBoxWithoutKeyboard') => void {
5
+ export default function useFocus(): (where?: 'main' | 'sendBox' | 'sendBoxWithoutKeyboard') => void {
6
6
  const { focusSendBoxCallbacksRef, focusTranscriptCallbacksRef } = useWebChatUIContext();
7
7
 
8
8
  return useCallback(
@@ -16,9 +16,8 @@ export default function useRenderMarkdownAsHTML(): (
16
16
 
17
17
  const externalLinkAlt = localize('MARKDOWN_EXTERNAL_LINK_ALT');
18
18
 
19
- return useMemo(() => renderMarkdown && (markdown => renderMarkdown(markdown, styleOptions, { externalLinkAlt })), [
20
- externalLinkAlt,
21
- renderMarkdown,
22
- styleOptions
23
- ]);
19
+ return useMemo(
20
+ () => renderMarkdown && (markdown => renderMarkdown(markdown, styleOptions, { externalLinkAlt })),
21
+ [externalLinkAlt, renderMarkdown, styleOptions]
22
+ );
24
23
  }
@@ -9,7 +9,8 @@ export default function useScrollTo(): (
9
9
  ) => void {
10
10
  const { scrollToCallbacksRef } = useWebChatUIContext();
11
11
 
12
- return useCallback((...args) => scrollToCallbacksRef.current.forEach(callback => callback(...args)), [
13
- scrollToCallbacksRef
14
- ]);
12
+ return useCallback(
13
+ (...args) => scrollToCallbacksRef.current.forEach(callback => callback(...args)),
14
+ [scrollToCallbacksRef]
15
+ );
15
16
  }
@@ -5,7 +5,8 @@ import useWebChatUIContext from './internal/useWebChatUIContext';
5
5
  export default function useScrollToEnd(): () => void {
6
6
  const { scrollToEndCallbacksRef } = useWebChatUIContext();
7
7
 
8
- return useCallback(() => scrollToEndCallbacksRef.current.forEach(callback => callback({ behavior: 'smooth' })), [
9
- scrollToEndCallbacksRef
10
- ]);
8
+ return useCallback(
9
+ () => scrollToEndCallbacksRef.current.forEach(callback => callback({ behavior: 'smooth' })),
10
+ [scrollToEndCallbacksRef]
11
+ );
11
12
  }
package/src/index.ts CHANGED
@@ -44,7 +44,6 @@ const hooks = {
44
44
  ...componentHooks
45
45
  };
46
46
 
47
- // eslint-disable-next-line no-undef
48
47
  const version = process.env.npm_package_version;
49
48
 
50
49
  const Components = {