@webiny/lexical-editor 6.3.0 → 6.4.0-beta.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (252) hide show
  1. package/commands/image.js +2 -1
  2. package/commands/image.js.map +1 -1
  3. package/commands/index.js +0 -2
  4. package/commands/list.js +4 -3
  5. package/commands/list.js.map +1 -1
  6. package/commands/quote.js +2 -1
  7. package/commands/quote.js.map +1 -1
  8. package/commands/toolbar.js +2 -1
  9. package/commands/toolbar.js.map +1 -1
  10. package/commands/typography.js +2 -1
  11. package/commands/typography.js.map +1 -1
  12. package/components/Editor/EnsureHeadingTagPlugin.js +8 -15
  13. package/components/Editor/EnsureHeadingTagPlugin.js.map +1 -1
  14. package/components/Editor/RichTextEditor.js +82 -121
  15. package/components/Editor/RichTextEditor.js.map +1 -1
  16. package/components/Editor/normalizeInputValue.js +11 -13
  17. package/components/Editor/normalizeInputValue.js.map +1 -1
  18. package/components/LexicalEditorConfig/LexicalEditorConfig.js +24 -15
  19. package/components/LexicalEditorConfig/LexicalEditorConfig.js.map +1 -1
  20. package/components/LexicalEditorConfig/components/Node.js +21 -26
  21. package/components/LexicalEditorConfig/components/Node.js.map +1 -1
  22. package/components/LexicalEditorConfig/components/Plugin.js +21 -26
  23. package/components/LexicalEditorConfig/components/Plugin.js.map +1 -1
  24. package/components/LexicalEditorConfig/components/ToolbarElement.js +21 -26
  25. package/components/LexicalEditorConfig/components/ToolbarElement.js.map +1 -1
  26. package/components/LexicalHtmlRenderer.js +35 -40
  27. package/components/LexicalHtmlRenderer.js.map +1 -1
  28. package/components/Toolbar/StaticToolbar.js +11 -16
  29. package/components/Toolbar/StaticToolbar.js.map +1 -1
  30. package/components/ToolbarActions/BoldAction.js +16 -19
  31. package/components/ToolbarActions/BoldAction.js.map +1 -1
  32. package/components/ToolbarActions/BulletListAction.js +24 -32
  33. package/components/ToolbarActions/BulletListAction.js.map +1 -1
  34. package/components/ToolbarActions/CodeHighlightAction.js +16 -19
  35. package/components/ToolbarActions/CodeHighlightAction.js.map +1 -1
  36. package/components/ToolbarActions/FontColorAction.js +32 -38
  37. package/components/ToolbarActions/FontColorAction.js.map +1 -1
  38. package/components/ToolbarActions/ImageAction.js +28 -30
  39. package/components/ToolbarActions/ImageAction.js.map +1 -1
  40. package/components/ToolbarActions/ItalicAction.js +16 -19
  41. package/components/ToolbarActions/ItalicAction.js.map +1 -1
  42. package/components/ToolbarActions/LinkAction.js +25 -30
  43. package/components/ToolbarActions/LinkAction.js.map +1 -1
  44. package/components/ToolbarActions/NumberedListAction.js +28 -37
  45. package/components/ToolbarActions/NumberedListAction.js.map +1 -1
  46. package/components/ToolbarActions/QuoteAction.js +22 -27
  47. package/components/ToolbarActions/QuoteAction.js.map +1 -1
  48. package/components/ToolbarActions/TextAlignmentAction.js +38 -50
  49. package/components/ToolbarActions/TextAlignmentAction.js.map +1 -1
  50. package/components/ToolbarActions/TypographyAction.js +69 -99
  51. package/components/ToolbarActions/TypographyAction.js.map +1 -1
  52. package/components/ToolbarActions/UnderlineAction.js +16 -19
  53. package/components/ToolbarActions/UnderlineAction.js.map +1 -1
  54. package/context/FontColorActionContext.js +3 -2
  55. package/context/FontColorActionContext.js.map +1 -1
  56. package/context/RichTextEditorContext.js +26 -29
  57. package/context/RichTextEditorContext.js.map +1 -1
  58. package/context/SharedHistoryContext.js +11 -15
  59. package/context/SharedHistoryContext.js.map +1 -1
  60. package/context/TextAlignmentActionContextProps.js +3 -2
  61. package/context/TextAlignmentActionContextProps.js.map +1 -1
  62. package/context/TypographyActionContext.js +3 -2
  63. package/context/TypographyActionContext.js.map +1 -1
  64. package/exports/admin/lexical.js +2 -20
  65. package/hooks/index.js +0 -2
  66. package/hooks/useCurrentElement.js +18 -21
  67. package/hooks/useCurrentElement.js.map +1 -1
  68. package/hooks/useCurrentSelection.js +39 -48
  69. package/hooks/useCurrentSelection.js.map +1 -1
  70. package/hooks/useFontColorPicker.js +5 -6
  71. package/hooks/useFontColorPicker.js.map +1 -1
  72. package/hooks/useIsMounted.js +7 -8
  73. package/hooks/useIsMounted.js.map +1 -1
  74. package/hooks/useRichTextEditor.js +5 -6
  75. package/hooks/useRichTextEditor.js.map +1 -1
  76. package/hooks/useTextAlignmentAction.js +5 -6
  77. package/hooks/useTextAlignmentAction.js.map +1 -1
  78. package/hooks/useTypographyAction.js +5 -6
  79. package/hooks/useTypographyAction.js.map +1 -1
  80. package/images/icons/chat-square-quote.js +19 -0
  81. package/images/icons/chat-square-quote.js.map +1 -0
  82. package/images/icons/chevron-down.js +18 -0
  83. package/images/icons/chevron-down.js.map +1 -0
  84. package/images/icons/code.js +17 -0
  85. package/images/icons/code.js.map +1 -0
  86. package/images/icons/font-color.js +17 -0
  87. package/images/icons/font-color.js.map +1 -0
  88. package/images/icons/indent.js +18 -0
  89. package/images/icons/indent.js.map +1 -0
  90. package/images/icons/insert-image.js +20 -0
  91. package/images/icons/insert-image.js.map +1 -0
  92. package/images/icons/justify.js +19 -0
  93. package/images/icons/justify.js.map +1 -0
  94. package/images/icons/link.js +19 -0
  95. package/images/icons/link.js.map +1 -0
  96. package/images/icons/list-ol.js +20 -0
  97. package/images/icons/list-ol.js.map +1 -0
  98. package/images/icons/list-ul.js +18 -0
  99. package/images/icons/list-ul.js.map +1 -0
  100. package/images/icons/outdent.js +18 -0
  101. package/images/icons/outdent.js.map +1 -0
  102. package/images/icons/pencil-fill.js +17 -0
  103. package/images/icons/pencil-fill.js.map +1 -0
  104. package/images/icons/text-center.js +18 -0
  105. package/images/icons/text-center.js.map +1 -0
  106. package/images/icons/text-left.js +18 -0
  107. package/images/icons/text-left.js.map +1 -0
  108. package/images/icons/text-paragraph.js +18 -0
  109. package/images/icons/text-paragraph.js.map +1 -0
  110. package/images/icons/text-right.js +18 -0
  111. package/images/icons/text-right.js.map +1 -0
  112. package/images/icons/type-bold.js +17 -0
  113. package/images/icons/type-bold.js.map +1 -0
  114. package/images/icons/type-h1.js +17 -0
  115. package/images/icons/type-h1.js.map +1 -0
  116. package/images/icons/type-h2.js +17 -0
  117. package/images/icons/type-h2.js.map +1 -0
  118. package/images/icons/type-h3.js +17 -0
  119. package/images/icons/type-h3.js.map +1 -0
  120. package/images/icons/type-h4.js +17 -0
  121. package/images/icons/type-h4.js.map +1 -0
  122. package/images/icons/type-h5.js +17 -0
  123. package/images/icons/type-h5.js.map +1 -0
  124. package/images/icons/type-h6.js +17 -0
  125. package/images/icons/type-h6.js.map +1 -0
  126. package/images/icons/type-italic.js +17 -0
  127. package/images/icons/type-italic.js.map +1 -0
  128. package/images/icons/type-strikethrough.js +17 -0
  129. package/images/icons/type-strikethrough.js.map +1 -0
  130. package/images/icons/type-underline.js +17 -0
  131. package/images/icons/type-underline.js.map +1 -0
  132. package/images/icons/unlink_icon.js +27 -0
  133. package/images/icons/unlink_icon.js.map +1 -0
  134. package/index.js +5 -18
  135. package/package.json +7 -7
  136. package/plugins/BlurEventPlugin/BlurEventPlugin.js +11 -14
  137. package/plugins/BlurEventPlugin/BlurEventPlugin.js.map +1 -1
  138. package/plugins/CodeHighlightPlugin/CodeHighlightPlugin.js +7 -8
  139. package/plugins/CodeHighlightPlugin/CodeHighlightPlugin.js.map +1 -1
  140. package/plugins/CodeHighlightPlugin/index.js +0 -2
  141. package/plugins/FloatingLinkEditorPlugin/FloatingLinkEditor.js +16 -24
  142. package/plugins/FloatingLinkEditorPlugin/FloatingLinkEditor.js.map +1 -1
  143. package/plugins/FloatingLinkEditorPlugin/FloatingLinkEditorController.js +37 -51
  144. package/plugins/FloatingLinkEditorPlugin/FloatingLinkEditorController.js.map +1 -1
  145. package/plugins/FloatingLinkEditorPlugin/FloatingLinkEditorPlugin.js +6 -5
  146. package/plugins/FloatingLinkEditorPlugin/FloatingLinkEditorPlugin.js.map +1 -1
  147. package/plugins/FloatingLinkEditorPlugin/index.js +0 -2
  148. package/plugins/FloatingLinkEditorPlugin/isChildOfLinkEditor.js +6 -9
  149. package/plugins/FloatingLinkEditorPlugin/isChildOfLinkEditor.js.map +1 -1
  150. package/plugins/FloatingLinkEditorPlugin/types.js +0 -3
  151. package/plugins/FloatingLinkEditorPlugin/useFloatingLinkEditor.js +101 -108
  152. package/plugins/FloatingLinkEditorPlugin/useFloatingLinkEditor.js.map +1 -1
  153. package/plugins/FontColorPlugin/FontColorPlugin.js +14 -19
  154. package/plugins/FontColorPlugin/FontColorPlugin.js.map +1 -1
  155. package/plugins/FontColorPlugin/applyColorToNode.js +5 -4
  156. package/plugins/FontColorPlugin/applyColorToNode.js.map +1 -1
  157. package/plugins/FontColorPlugin/applyColorToSelection.js +42 -60
  158. package/plugins/FontColorPlugin/applyColorToSelection.js.map +1 -1
  159. package/plugins/ImagesPlugin/ImagesPlugin.js +79 -121
  160. package/plugins/ImagesPlugin/ImagesPlugin.js.map +1 -1
  161. package/plugins/LinkPlugin/LinkPlugin.js +46 -52
  162. package/plugins/LinkPlugin/LinkPlugin.js.map +1 -1
  163. package/plugins/ListPLugin/ListPlugin.js +44 -52
  164. package/plugins/ListPLugin/ListPlugin.js.map +1 -1
  165. package/plugins/QuoteNodePlugin/QuoteNodePlugin.js +18 -19
  166. package/plugins/QuoteNodePlugin/QuoteNodePlugin.js.map +1 -1
  167. package/plugins/StateHandlingPlugin.js +55 -64
  168. package/plugins/StateHandlingPlugin.js.map +1 -1
  169. package/plugins/TypographyPlugin/TypographyPlugin.js +13 -20
  170. package/plugins/TypographyPlugin/TypographyPlugin.js.map +1 -1
  171. package/static/svg/chat-square-quote.123cfa24.svg +1 -0
  172. package/static/svg/chevron-down.d9636921.svg +1 -0
  173. package/static/svg/code.912b1f4d.svg +1 -0
  174. package/static/svg/font-color.4f0c0de5.svg +1 -0
  175. package/static/svg/indent.4d78e483.svg +3 -0
  176. package/static/svg/insert-image.354465f1.svg +4 -0
  177. package/static/svg/justify.dab42aec.svg +3 -0
  178. package/static/svg/link.b774de25.svg +1 -0
  179. package/static/svg/list-ol.d64946f3.svg +1 -0
  180. package/static/svg/list-ul.1d54da3f.svg +1 -0
  181. package/static/svg/outdent.5c13ff16.svg +3 -0
  182. package/static/svg/pencil-fill.94cb216b.svg +1 -0
  183. package/static/svg/text-center.a411e780.svg +1 -0
  184. package/static/svg/text-left.54f41f4e.svg +1 -0
  185. package/static/svg/text-paragraph.61674422.svg +1 -0
  186. package/static/svg/text-right.9288b7a2.svg +1 -0
  187. package/static/svg/type-bold.7e3e270b.svg +1 -0
  188. package/static/svg/type-h1.f292ffe1.svg +1 -0
  189. package/static/svg/type-h2.a9d1aa48.svg +1 -0
  190. package/static/svg/type-h3.4a29ff88.svg +1 -0
  191. package/static/svg/type-h4.7f48750c.svg +1 -0
  192. package/static/svg/type-h5.14b4ac56.svg +1 -0
  193. package/static/svg/type-h6.4e9dfe2d.svg +1 -0
  194. package/static/svg/type-italic.d8e45748.svg +1 -0
  195. package/static/svg/type-strikethrough.2694a816.svg +1 -0
  196. package/static/svg/type-underline.104a0ed5.svg +1 -0
  197. package/static/svg/unlink_icon.074ceed3.svg +1 -0
  198. package/types.js +0 -8
  199. package/ui/ContentEditable.js +6 -14
  200. package/ui/ContentEditable.js.map +1 -1
  201. package/ui/Divider.js +6 -5
  202. package/ui/Divider.js.map +1 -1
  203. package/ui/DropDown.js +146 -176
  204. package/ui/DropDown.js.map +1 -1
  205. package/ui/ImageResizer.js +173 -204
  206. package/ui/ImageResizer.js.map +1 -1
  207. package/ui/LinkPreview.js +61 -84
  208. package/ui/LinkPreview.js.map +1 -1
  209. package/ui/Placeholder.js +9 -20
  210. package/ui/Placeholder.js.map +1 -1
  211. package/ui/TextInput.js +17 -30
  212. package/ui/TextInput.js.map +1 -1
  213. package/ui/ToolbarActionDialog.js +64 -73
  214. package/ui/ToolbarActionDialog.js.map +1 -1
  215. package/utils/canUseDOM.js +2 -1
  216. package/utils/canUseDOM.js.map +1 -1
  217. package/utils/files.js +9 -8
  218. package/utils/files.js.map +1 -1
  219. package/utils/getDOMRangeRect.js +10 -20
  220. package/utils/getDOMRangeRect.js.map +1 -1
  221. package/utils/getSelectedNode.js +9 -20
  222. package/utils/getSelectedNode.js.map +1 -1
  223. package/utils/getTransparentImage.js +2 -3
  224. package/utils/getTransparentImage.js.map +1 -1
  225. package/utils/insertImage.js +9 -11
  226. package/utils/insertImage.js.map +1 -1
  227. package/utils/isAnchorLink.js +2 -3
  228. package/utils/isAnchorLink.js.map +1 -1
  229. package/utils/isChildOfFloatingToolbar.js +6 -9
  230. package/utils/isChildOfFloatingToolbar.js.map +1 -1
  231. package/utils/isHTMLElement.js +3 -9
  232. package/utils/isHTMLElement.js.map +1 -1
  233. package/utils/isValidJSON.js +9 -10
  234. package/utils/isValidJSON.js.map +1 -1
  235. package/utils/isValidLexicalData.js +17 -20
  236. package/utils/isValidLexicalData.js.map +1 -1
  237. package/utils/point.js +32 -45
  238. package/utils/point.js.map +1 -1
  239. package/utils/rect.js +92 -125
  240. package/utils/rect.js.map +1 -1
  241. package/utils/sanitizeUrl.js +8 -21
  242. package/utils/sanitizeUrl.js.map +1 -1
  243. package/utils/setFloatingElemPosition.js +23 -27
  244. package/utils/setFloatingElemPosition.js.map +1 -1
  245. package/commands/index.js.map +0 -1
  246. package/exports/admin/lexical.js.map +0 -1
  247. package/hooks/index.js.map +0 -1
  248. package/index.js.map +0 -1
  249. package/plugins/CodeHighlightPlugin/index.js.map +0 -1
  250. package/plugins/FloatingLinkEditorPlugin/index.js.map +0 -1
  251. package/plugins/FloatingLinkEditorPlugin/types.js.map +0 -1
  252. package/types.js.map +0 -1
@@ -1 +1 @@
1
- {"version":3,"names":["ContentEditable","React","LexicalContentEditable","className","createElement"],"sources":["ContentEditable.tsx"],"sourcesContent":["/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\nimport \"./ContentEditable.css\";\n\nimport { ContentEditable } from \"@lexical/react/LexicalContentEditable\";\nimport * as React from \"react\";\n\nexport function LexicalContentEditable({ className }: { className?: string }): React.JSX.Element {\n return <ContentEditable className={className || \"ContentEditable__root\"} />;\n}\n"],"mappings":"AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AAEA,SAASA,eAAe,QAAQ,uCAAuC;AACvE,OAAO,KAAKC,KAAK,MAAM,OAAO;AAE9B,OAAO,SAASC,sBAAsBA,CAAC;EAAEC;AAAkC,CAAC,EAAqB;EAC7F,oBAAOF,KAAA,CAAAG,aAAA,CAACJ,eAAe;IAACG,SAAS,EAAEA,SAAS,IAAI;EAAwB,CAAE,CAAC;AAC/E","ignoreList":[]}
1
+ {"version":3,"file":"ui/ContentEditable.js","sources":["../../src/ui/ContentEditable.tsx"],"sourcesContent":["/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\nimport \"./ContentEditable.css\";\n\nimport { ContentEditable } from \"@lexical/react/LexicalContentEditable\";\nimport * as React from \"react\";\n\nexport function LexicalContentEditable({ className }: { className?: string }): React.JSX.Element {\n return <ContentEditable className={className || \"ContentEditable__root\"} />;\n}\n"],"names":["LexicalContentEditable","className","ContentEditable"],"mappings":";;;AAYO,SAASA,uBAAuB,EAAEC,SAAS,EAA0B;IACxE,OAAO,WAAP,GAAO,sCAACC,iBAAeA;QAAC,WAAWD,aAAa;;AACpD"}
package/ui/Divider.js CHANGED
@@ -1,8 +1,9 @@
1
- import React from "react";
2
- export function Divider() {
3
- return /*#__PURE__*/React.createElement("div", {
4
- className: "divider"
5
- });
1
+ import react from "react";
2
+ function Divider() {
3
+ return /*#__PURE__*/ react.createElement("div", {
4
+ className: "divider"
5
+ });
6
6
  }
7
+ export { Divider };
7
8
 
8
9
  //# sourceMappingURL=Divider.js.map
package/ui/Divider.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"names":["React","Divider","createElement","className"],"sources":["Divider.tsx"],"sourcesContent":["import React from \"react\";\n\nexport function Divider(): React.JSX.Element {\n return <div className=\"divider\"></div>;\n}\n"],"mappings":"AAAA,OAAOA,KAAK,MAAM,OAAO;AAEzB,OAAO,SAASC,OAAOA,CAAA,EAAsB;EACzC,oBAAOD,KAAA,CAAAE,aAAA;IAAKC,SAAS,EAAC;EAAS,CAAM,CAAC;AAC1C","ignoreList":[]}
1
+ {"version":3,"file":"ui/Divider.js","sources":["../../src/ui/Divider.tsx"],"sourcesContent":["import React from \"react\";\n\nexport function Divider(): React.JSX.Element {\n return <div className=\"divider\"></div>;\n}\n"],"names":["Divider"],"mappings":";AAEO,SAASA;IACZ,OAAO,WAAP,GAAO,oBAAC;QAAI,WAAU;;AAC1B"}
package/ui/DropDown.js CHANGED
@@ -1,183 +1,153 @@
1
- /**
2
- * Copyright (c) Meta Platforms, Inc. and affiliates.
3
- *
4
- * This source code is licensed under the MIT license found in the
5
- * LICENSE file in the root directory of this source tree.
6
- *
7
- */
8
-
9
- import * as React from "react";
10
- import { useCallback, useEffect, useMemo, useRef, useState } from "react";
11
- const DropDownContext = /*#__PURE__*/React.createContext(null);
12
- export function DropDownItem({
13
- children,
14
- className,
15
- onClick,
16
- title
17
- }) {
18
- const ref = useRef(null);
19
- const dropDownContext = React.useContext(DropDownContext);
20
- if (dropDownContext === null) {
21
- throw new Error("DropDownItem must be used within a DropDown");
22
- }
23
- const {
24
- registerItem
25
- } = dropDownContext;
26
- useEffect(() => {
27
- if (!ref.current) {
28
- return;
29
- }
30
- registerItem(ref);
31
- }, [ref, registerItem]);
32
- return /*#__PURE__*/React.createElement("button", {
33
- className: className,
34
- onClick: onClick,
35
- ref: ref,
36
- title: title,
37
- type: "button"
38
- }, children);
1
+ import * as __rspack_external_react from "react";
2
+ const DropDownContext = /*#__PURE__*/ __rspack_external_react.createContext(null);
3
+ function DropDownItem({ children, className, onClick, title }) {
4
+ const ref = (0, __rspack_external_react.useRef)(null);
5
+ const dropDownContext = __rspack_external_react.useContext(DropDownContext);
6
+ if (null === dropDownContext) throw new Error("DropDownItem must be used within a DropDown");
7
+ const { registerItem } = dropDownContext;
8
+ (0, __rspack_external_react.useEffect)(()=>{
9
+ if (!ref.current) return;
10
+ registerItem(ref);
11
+ }, [
12
+ ref,
13
+ registerItem
14
+ ]);
15
+ return /*#__PURE__*/ __rspack_external_react.createElement("button", {
16
+ className: className,
17
+ onClick: onClick,
18
+ ref: ref,
19
+ title: title,
20
+ type: "button"
21
+ }, children);
39
22
  }
40
- function DropDownItems({
41
- children,
42
- dropDownRef,
43
- showScroll = true,
44
- onClose
45
- }) {
46
- const [items, setItems] = useState();
47
- const [highlightedItem, setHighlightedItem] = useState();
48
- const registerItem = useCallback(itemRef => {
49
- setItems(prev => prev ? [...prev, itemRef] : [itemRef]);
50
- }, [setItems]);
51
- const handleKeyDown = event => {
52
- if (!items) {
53
- return;
54
- }
55
- const key = event.key;
56
- if (["Escape", "ArrowUp", "ArrowDown", "Tab"].includes(key)) {
57
- event.preventDefault();
58
- }
59
- if (key === "Escape" || key === "Tab") {
60
- onClose();
61
- } else if (key === "ArrowUp") {
62
- setHighlightedItem(prev => {
63
- if (!prev) {
64
- return items[0];
65
- }
66
- const index = items.indexOf(prev) - 1;
67
- return items[index === -1 ? items.length - 1 : index];
68
- });
69
- } else if (key === "ArrowDown") {
70
- setHighlightedItem(prev => {
71
- if (!prev) {
72
- return items[0];
73
- }
74
- return items[items.indexOf(prev) + 1];
75
- });
76
- }
77
- };
78
- const contextValue = useMemo(() => ({
79
- registerItem
80
- }), [registerItem]);
81
- useEffect(() => {
82
- if (items && !highlightedItem) {
83
- setHighlightedItem(items[0]);
84
- }
85
- if (highlightedItem && highlightedItem.current) {
86
- highlightedItem.current.focus();
87
- }
88
- }, [items, highlightedItem]);
89
- return /*#__PURE__*/React.createElement(DropDownContext.Provider, {
90
- value: contextValue
91
- }, /*#__PURE__*/React.createElement("div", {
92
- className: `lexical-dropdown ${showScroll ? "" : "no-scroll"}`,
93
- ref: dropDownRef,
94
- onKeyDown: handleKeyDown
95
- }, children));
23
+ function DropDownItems({ children, dropDownRef, showScroll = true, onClose }) {
24
+ const [items, setItems] = (0, __rspack_external_react.useState)();
25
+ const [highlightedItem, setHighlightedItem] = (0, __rspack_external_react.useState)();
26
+ const registerItem = (0, __rspack_external_react.useCallback)((itemRef)=>{
27
+ setItems((prev)=>prev ? [
28
+ ...prev,
29
+ itemRef
30
+ ] : [
31
+ itemRef
32
+ ]);
33
+ }, [
34
+ setItems
35
+ ]);
36
+ const handleKeyDown = (event)=>{
37
+ if (!items) return;
38
+ const key = event.key;
39
+ if ([
40
+ "Escape",
41
+ "ArrowUp",
42
+ "ArrowDown",
43
+ "Tab"
44
+ ].includes(key)) event.preventDefault();
45
+ if ("Escape" === key || "Tab" === key) onClose();
46
+ else if ("ArrowUp" === key) setHighlightedItem((prev)=>{
47
+ if (!prev) return items[0];
48
+ const index = items.indexOf(prev) - 1;
49
+ return items[-1 === index ? items.length - 1 : index];
50
+ });
51
+ else if ("ArrowDown" === key) setHighlightedItem((prev)=>{
52
+ if (!prev) return items[0];
53
+ return items[items.indexOf(prev) + 1];
54
+ });
55
+ };
56
+ const contextValue = (0, __rspack_external_react.useMemo)(()=>({
57
+ registerItem
58
+ }), [
59
+ registerItem
60
+ ]);
61
+ (0, __rspack_external_react.useEffect)(()=>{
62
+ if (items && !highlightedItem) setHighlightedItem(items[0]);
63
+ if (highlightedItem && highlightedItem.current) highlightedItem.current.focus();
64
+ }, [
65
+ items,
66
+ highlightedItem
67
+ ]);
68
+ return /*#__PURE__*/ __rspack_external_react.createElement(DropDownContext.Provider, {
69
+ value: contextValue
70
+ }, /*#__PURE__*/ __rspack_external_react.createElement("div", {
71
+ className: `lexical-dropdown ${showScroll ? "" : "no-scroll"}`,
72
+ ref: dropDownRef,
73
+ onKeyDown: handleKeyDown
74
+ }, children));
96
75
  }
97
- export function DropDown({
98
- disabled = false,
99
- buttonLabel,
100
- buttonAriaLabel,
101
- buttonClassName,
102
- buttonIconClassName,
103
- children,
104
- stopCloseOnClickSelf,
105
- showScroll = true
106
- }) {
107
- const dropDownRef = useRef(null);
108
- const buttonRef = useRef(null);
109
- // Used to prevent flickering of the dropdown while calculating the dropdown position.
110
- const [positionIsCalculated, setPositionIsCalculated] = useState(false);
111
- const [showDropDown, setShowDropDown] = useState(false);
112
- const handleClose = () => {
113
- setPositionIsCalculated(false);
114
- setShowDropDown(false);
115
- if (buttonRef && buttonRef.current) {
116
- buttonRef.current.focus();
117
- }
118
- };
119
- useEffect(() => {
120
- const button = buttonRef.current;
121
- const dropDown = dropDownRef.current;
122
- if (showDropDown && button && dropDown) {
123
- dropDown.style.top = "44px";
124
- dropDown.style.left = `${button.offsetLeft}px`;
125
- setPositionIsCalculated(true);
126
- }
127
- }, [dropDownRef, buttonRef, showDropDown]);
128
- useEffect(() => {
129
- const button = buttonRef.current;
130
- if (button && showDropDown) {
131
- const handle = event => {
132
- const target = event.target;
133
- if (stopCloseOnClickSelf) {
134
- if (dropDownRef.current && dropDownRef.current.contains(target)) {
135
- return;
136
- }
76
+ function DropDown({ disabled = false, buttonLabel, buttonAriaLabel, buttonClassName, buttonIconClassName, children, stopCloseOnClickSelf, showScroll = true }) {
77
+ const dropDownRef = (0, __rspack_external_react.useRef)(null);
78
+ const buttonRef = (0, __rspack_external_react.useRef)(null);
79
+ const [positionIsCalculated, setPositionIsCalculated] = (0, __rspack_external_react.useState)(false);
80
+ const [showDropDown, setShowDropDown] = (0, __rspack_external_react.useState)(false);
81
+ const handleClose = ()=>{
82
+ setPositionIsCalculated(false);
83
+ setShowDropDown(false);
84
+ if (buttonRef && buttonRef.current) buttonRef.current.focus();
85
+ };
86
+ (0, __rspack_external_react.useEffect)(()=>{
87
+ const button = buttonRef.current;
88
+ const dropDown = dropDownRef.current;
89
+ if (showDropDown && button && dropDown) {
90
+ dropDown.style.top = "44px";
91
+ dropDown.style.left = `${button.offsetLeft}px`;
92
+ setPositionIsCalculated(true);
137
93
  }
138
- if (!button.contains(target)) {
139
- setShowDropDown(false);
94
+ }, [
95
+ dropDownRef,
96
+ buttonRef,
97
+ showDropDown
98
+ ]);
99
+ (0, __rspack_external_react.useEffect)(()=>{
100
+ const button = buttonRef.current;
101
+ if (button && showDropDown) {
102
+ const handle = (event)=>{
103
+ const target = event.target;
104
+ if (stopCloseOnClickSelf) {
105
+ if (dropDownRef.current && dropDownRef.current.contains(target)) return;
106
+ }
107
+ if (!button.contains(target)) setShowDropDown(false);
108
+ };
109
+ document.addEventListener("click", handle);
110
+ return ()=>{
111
+ document.removeEventListener("click", handle);
112
+ };
140
113
  }
141
- };
142
- document.addEventListener("click", handle);
143
- return () => {
144
- document.removeEventListener("click", handle);
145
- };
146
- }
147
- return;
148
- }, [dropDownRef, buttonRef, showDropDown, stopCloseOnClickSelf]);
149
- const displayContainer = useMemo(() => {
150
- // To prevent blinking, we show the container only when the dropdown position is calculated.
151
- // Without this, window would be visible first on left (0px), and after a millisecond on the right side.
152
- return positionIsCalculated ? {
153
- display: "block"
154
- } : {
155
- display: "none"
156
- };
157
- }, [positionIsCalculated]);
158
- return /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement("button", {
159
- style: {
160
- position: "relative"
161
- },
162
- disabled: disabled,
163
- "aria-label": buttonAriaLabel || buttonLabel,
164
- className: buttonClassName,
165
- onClick: () => setShowDropDown(!showDropDown),
166
- ref: buttonRef
167
- }, buttonIconClassName && /*#__PURE__*/React.createElement("span", {
168
- className: buttonIconClassName
169
- }), buttonLabel && /*#__PURE__*/React.createElement("span", {
170
- className: "text dropdown-button-text"
171
- }, buttonLabel), /*#__PURE__*/React.createElement("i", {
172
- className: "chevron-down"
173
- })), showDropDown && /*#__PURE__*/React.createElement("div", {
174
- className: "lexical-dropdown-container",
175
- style: displayContainer
176
- }, /*#__PURE__*/React.createElement(DropDownItems, {
177
- showScroll: showScroll,
178
- dropDownRef: dropDownRef,
179
- onClose: handleClose
180
- }, children)));
114
+ }, [
115
+ dropDownRef,
116
+ buttonRef,
117
+ showDropDown,
118
+ stopCloseOnClickSelf
119
+ ]);
120
+ const displayContainer = (0, __rspack_external_react.useMemo)(()=>positionIsCalculated ? {
121
+ display: "block"
122
+ } : {
123
+ display: "none"
124
+ }, [
125
+ positionIsCalculated
126
+ ]);
127
+ return /*#__PURE__*/ __rspack_external_react.createElement(__rspack_external_react.Fragment, null, /*#__PURE__*/ __rspack_external_react.createElement("button", {
128
+ style: {
129
+ position: "relative"
130
+ },
131
+ disabled: disabled,
132
+ "aria-label": buttonAriaLabel || buttonLabel,
133
+ className: buttonClassName,
134
+ onClick: ()=>setShowDropDown(!showDropDown),
135
+ ref: buttonRef
136
+ }, buttonIconClassName && /*#__PURE__*/ __rspack_external_react.createElement("span", {
137
+ className: buttonIconClassName
138
+ }), buttonLabel && /*#__PURE__*/ __rspack_external_react.createElement("span", {
139
+ className: "text dropdown-button-text"
140
+ }, buttonLabel), /*#__PURE__*/ __rspack_external_react.createElement("i", {
141
+ className: "chevron-down"
142
+ })), showDropDown && /*#__PURE__*/ __rspack_external_react.createElement("div", {
143
+ className: "lexical-dropdown-container",
144
+ style: displayContainer
145
+ }, /*#__PURE__*/ __rspack_external_react.createElement(DropDownItems, {
146
+ showScroll: showScroll,
147
+ dropDownRef: dropDownRef,
148
+ onClose: handleClose
149
+ }, children)));
181
150
  }
151
+ export { DropDown, DropDownItem };
182
152
 
183
153
  //# sourceMappingURL=DropDown.js.map
@@ -1 +1 @@
1
- {"version":3,"names":["React","useCallback","useEffect","useMemo","useRef","useState","DropDownContext","createContext","DropDownItem","children","className","onClick","title","ref","dropDownContext","useContext","Error","registerItem","current","createElement","type","DropDownItems","dropDownRef","showScroll","onClose","items","setItems","highlightedItem","setHighlightedItem","itemRef","prev","handleKeyDown","event","key","includes","preventDefault","index","indexOf","length","contextValue","focus","Provider","value","onKeyDown","DropDown","disabled","buttonLabel","buttonAriaLabel","buttonClassName","buttonIconClassName","stopCloseOnClickSelf","buttonRef","positionIsCalculated","setPositionIsCalculated","showDropDown","setShowDropDown","handleClose","button","dropDown","style","top","left","offsetLeft","handle","target","contains","document","addEventListener","removeEventListener","displayContainer","display","Fragment","position"],"sources":["DropDown.tsx"],"sourcesContent":["/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\nimport type { ReactNode, RefObject } from \"react\";\nimport * as React from \"react\";\nimport { useCallback, useEffect, useMemo, useRef, useState } from \"react\";\n\ntype DropDownContextType = {\n registerItem: (ref: React.RefObject<HTMLButtonElement>) => void;\n};\n\nconst DropDownContext = React.createContext<DropDownContextType | null>(null);\n\nexport function DropDownItem({\n children,\n className,\n onClick,\n title\n}: {\n children: React.ReactNode;\n className: string;\n onClick: (event: React.MouseEvent<HTMLButtonElement>) => void;\n title?: string;\n}) {\n const ref = useRef<HTMLButtonElement>(null);\n\n const dropDownContext = React.useContext(DropDownContext);\n\n if (dropDownContext === null) {\n throw new Error(\"DropDownItem must be used within a DropDown\");\n }\n\n const { registerItem } = dropDownContext;\n\n useEffect(() => {\n if (!ref.current) {\n return;\n }\n\n registerItem(ref as RefObject<HTMLButtonElement>);\n }, [ref, registerItem]);\n\n return (\n <button className={className} onClick={onClick} ref={ref} title={title} type=\"button\">\n {children}\n </button>\n );\n}\n\nfunction DropDownItems({\n children,\n dropDownRef,\n showScroll = true,\n onClose\n}: {\n children: React.ReactNode;\n dropDownRef?: React.Ref<HTMLDivElement>;\n showScroll?: boolean;\n onClose: () => void;\n}) {\n const [items, setItems] = useState<React.RefObject<HTMLButtonElement>[]>();\n const [highlightedItem, setHighlightedItem] = useState<React.RefObject<HTMLButtonElement>>();\n\n const registerItem = useCallback(\n (itemRef: React.RefObject<HTMLButtonElement>) => {\n setItems(prev => (prev ? [...prev, itemRef] : [itemRef]));\n },\n [setItems]\n );\n\n const handleKeyDown = (event: React.KeyboardEvent<HTMLDivElement>) => {\n if (!items) {\n return;\n }\n\n const key = event.key;\n\n if ([\"Escape\", \"ArrowUp\", \"ArrowDown\", \"Tab\"].includes(key)) {\n event.preventDefault();\n }\n\n if (key === \"Escape\" || key === \"Tab\") {\n onClose();\n } else if (key === \"ArrowUp\") {\n setHighlightedItem(prev => {\n if (!prev) {\n return items[0];\n }\n const index = items.indexOf(prev) - 1;\n return items[index === -1 ? items.length - 1 : index];\n });\n } else if (key === \"ArrowDown\") {\n setHighlightedItem(prev => {\n if (!prev) {\n return items[0];\n }\n return items[items.indexOf(prev) + 1];\n });\n }\n };\n\n const contextValue = useMemo(\n () => ({\n registerItem\n }),\n [registerItem]\n );\n\n useEffect(() => {\n if (items && !highlightedItem) {\n setHighlightedItem(items[0]);\n }\n\n if (highlightedItem && highlightedItem.current) {\n highlightedItem.current.focus();\n }\n }, [items, highlightedItem]);\n\n return (\n <DropDownContext.Provider value={contextValue}>\n <div\n className={`lexical-dropdown ${showScroll ? \"\" : \"no-scroll\"}`}\n ref={dropDownRef}\n onKeyDown={handleKeyDown}\n >\n {children}\n </div>\n </DropDownContext.Provider>\n );\n}\n\nexport function DropDown({\n disabled = false,\n buttonLabel,\n buttonAriaLabel,\n buttonClassName,\n buttonIconClassName,\n children,\n stopCloseOnClickSelf,\n showScroll = true\n}: {\n disabled?: boolean;\n buttonAriaLabel?: string;\n buttonClassName: string;\n buttonIconClassName?: string;\n buttonLabel?: string;\n children: ReactNode;\n stopCloseOnClickSelf?: boolean;\n showScroll?: boolean;\n}): React.JSX.Element {\n const dropDownRef = useRef<HTMLDivElement>(null);\n const buttonRef = useRef<HTMLButtonElement>(null);\n // Used to prevent flickering of the dropdown while calculating the dropdown position.\n const [positionIsCalculated, setPositionIsCalculated] = useState(false);\n const [showDropDown, setShowDropDown] = useState(false);\n\n const handleClose = () => {\n setPositionIsCalculated(false);\n setShowDropDown(false);\n if (buttonRef && buttonRef.current) {\n buttonRef.current.focus();\n }\n };\n\n useEffect(() => {\n const button = buttonRef.current;\n const dropDown = dropDownRef.current;\n\n if (showDropDown && button && dropDown) {\n dropDown.style.top = \"44px\";\n dropDown.style.left = `${button.offsetLeft}px`;\n setPositionIsCalculated(true);\n }\n }, [dropDownRef, buttonRef, showDropDown]);\n\n useEffect(() => {\n const button = buttonRef.current;\n if (button && showDropDown) {\n const handle = (event: MouseEvent) => {\n const target = event.target;\n if (stopCloseOnClickSelf) {\n if (dropDownRef.current && dropDownRef.current.contains(target as Node)) {\n return;\n }\n }\n\n if (!button.contains(target as Node)) {\n setShowDropDown(false);\n }\n };\n document.addEventListener(\"click\", handle);\n return () => {\n document.removeEventListener(\"click\", handle);\n };\n }\n return;\n }, [dropDownRef, buttonRef, showDropDown, stopCloseOnClickSelf]);\n\n const displayContainer = useMemo(() => {\n // To prevent blinking, we show the container only when the dropdown position is calculated.\n // Without this, window would be visible first on left (0px), and after a millisecond on the right side.\n return positionIsCalculated ? { display: \"block\" } : { display: \"none\" };\n }, [positionIsCalculated]);\n\n return (\n <>\n <button\n style={{ position: \"relative\" }}\n disabled={disabled}\n aria-label={buttonAriaLabel || buttonLabel}\n className={buttonClassName}\n onClick={() => setShowDropDown(!showDropDown)}\n ref={buttonRef}\n >\n {buttonIconClassName && <span className={buttonIconClassName} />}\n {buttonLabel && <span className=\"text dropdown-button-text\">{buttonLabel}</span>}\n <i className=\"chevron-down\" />\n </button>\n {showDropDown && (\n <div className={\"lexical-dropdown-container\"} style={displayContainer}>\n <DropDownItems\n showScroll={showScroll}\n dropDownRef={dropDownRef}\n onClose={handleClose}\n >\n {children}\n </DropDownItems>\n </div>\n )}\n </>\n );\n}\n"],"mappings":"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","ignoreList":[]}
1
+ {"version":3,"file":"ui/DropDown.js","sources":["../../src/ui/DropDown.tsx"],"sourcesContent":["/**\n * Copyright (c) Meta Platforms, Inc. and affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n *\n */\n\nimport type { ReactNode, RefObject } from \"react\";\nimport * as React from \"react\";\nimport { useCallback, useEffect, useMemo, useRef, useState } from \"react\";\n\ntype DropDownContextType = {\n registerItem: (ref: React.RefObject<HTMLButtonElement>) => void;\n};\n\nconst DropDownContext = React.createContext<DropDownContextType | null>(null);\n\nexport function DropDownItem({\n children,\n className,\n onClick,\n title\n}: {\n children: React.ReactNode;\n className: string;\n onClick: (event: React.MouseEvent<HTMLButtonElement>) => void;\n title?: string;\n}) {\n const ref = useRef<HTMLButtonElement>(null);\n\n const dropDownContext = React.useContext(DropDownContext);\n\n if (dropDownContext === null) {\n throw new Error(\"DropDownItem must be used within a DropDown\");\n }\n\n const { registerItem } = dropDownContext;\n\n useEffect(() => {\n if (!ref.current) {\n return;\n }\n\n registerItem(ref as RefObject<HTMLButtonElement>);\n }, [ref, registerItem]);\n\n return (\n <button className={className} onClick={onClick} ref={ref} title={title} type=\"button\">\n {children}\n </button>\n );\n}\n\nfunction DropDownItems({\n children,\n dropDownRef,\n showScroll = true,\n onClose\n}: {\n children: React.ReactNode;\n dropDownRef?: React.Ref<HTMLDivElement>;\n showScroll?: boolean;\n onClose: () => void;\n}) {\n const [items, setItems] = useState<React.RefObject<HTMLButtonElement>[]>();\n const [highlightedItem, setHighlightedItem] = useState<React.RefObject<HTMLButtonElement>>();\n\n const registerItem = useCallback(\n (itemRef: React.RefObject<HTMLButtonElement>) => {\n setItems(prev => (prev ? [...prev, itemRef] : [itemRef]));\n },\n [setItems]\n );\n\n const handleKeyDown = (event: React.KeyboardEvent<HTMLDivElement>) => {\n if (!items) {\n return;\n }\n\n const key = event.key;\n\n if ([\"Escape\", \"ArrowUp\", \"ArrowDown\", \"Tab\"].includes(key)) {\n event.preventDefault();\n }\n\n if (key === \"Escape\" || key === \"Tab\") {\n onClose();\n } else if (key === \"ArrowUp\") {\n setHighlightedItem(prev => {\n if (!prev) {\n return items[0];\n }\n const index = items.indexOf(prev) - 1;\n return items[index === -1 ? items.length - 1 : index];\n });\n } else if (key === \"ArrowDown\") {\n setHighlightedItem(prev => {\n if (!prev) {\n return items[0];\n }\n return items[items.indexOf(prev) + 1];\n });\n }\n };\n\n const contextValue = useMemo(\n () => ({\n registerItem\n }),\n [registerItem]\n );\n\n useEffect(() => {\n if (items && !highlightedItem) {\n setHighlightedItem(items[0]);\n }\n\n if (highlightedItem && highlightedItem.current) {\n highlightedItem.current.focus();\n }\n }, [items, highlightedItem]);\n\n return (\n <DropDownContext.Provider value={contextValue}>\n <div\n className={`lexical-dropdown ${showScroll ? \"\" : \"no-scroll\"}`}\n ref={dropDownRef}\n onKeyDown={handleKeyDown}\n >\n {children}\n </div>\n </DropDownContext.Provider>\n );\n}\n\nexport function DropDown({\n disabled = false,\n buttonLabel,\n buttonAriaLabel,\n buttonClassName,\n buttonIconClassName,\n children,\n stopCloseOnClickSelf,\n showScroll = true\n}: {\n disabled?: boolean;\n buttonAriaLabel?: string;\n buttonClassName: string;\n buttonIconClassName?: string;\n buttonLabel?: string;\n children: ReactNode;\n stopCloseOnClickSelf?: boolean;\n showScroll?: boolean;\n}): React.JSX.Element {\n const dropDownRef = useRef<HTMLDivElement>(null);\n const buttonRef = useRef<HTMLButtonElement>(null);\n // Used to prevent flickering of the dropdown while calculating the dropdown position.\n const [positionIsCalculated, setPositionIsCalculated] = useState(false);\n const [showDropDown, setShowDropDown] = useState(false);\n\n const handleClose = () => {\n setPositionIsCalculated(false);\n setShowDropDown(false);\n if (buttonRef && buttonRef.current) {\n buttonRef.current.focus();\n }\n };\n\n useEffect(() => {\n const button = buttonRef.current;\n const dropDown = dropDownRef.current;\n\n if (showDropDown && button && dropDown) {\n dropDown.style.top = \"44px\";\n dropDown.style.left = `${button.offsetLeft}px`;\n setPositionIsCalculated(true);\n }\n }, [dropDownRef, buttonRef, showDropDown]);\n\n useEffect(() => {\n const button = buttonRef.current;\n if (button && showDropDown) {\n const handle = (event: MouseEvent) => {\n const target = event.target;\n if (stopCloseOnClickSelf) {\n if (dropDownRef.current && dropDownRef.current.contains(target as Node)) {\n return;\n }\n }\n\n if (!button.contains(target as Node)) {\n setShowDropDown(false);\n }\n };\n document.addEventListener(\"click\", handle);\n return () => {\n document.removeEventListener(\"click\", handle);\n };\n }\n return;\n }, [dropDownRef, buttonRef, showDropDown, stopCloseOnClickSelf]);\n\n const displayContainer = useMemo(() => {\n // To prevent blinking, we show the container only when the dropdown position is calculated.\n // Without this, window would be visible first on left (0px), and after a millisecond on the right side.\n return positionIsCalculated ? { display: \"block\" } : { display: \"none\" };\n }, [positionIsCalculated]);\n\n return (\n <>\n <button\n style={{ position: \"relative\" }}\n disabled={disabled}\n aria-label={buttonAriaLabel || buttonLabel}\n className={buttonClassName}\n onClick={() => setShowDropDown(!showDropDown)}\n ref={buttonRef}\n >\n {buttonIconClassName && <span className={buttonIconClassName} />}\n {buttonLabel && <span className=\"text dropdown-button-text\">{buttonLabel}</span>}\n <i className=\"chevron-down\" />\n </button>\n {showDropDown && (\n <div className={\"lexical-dropdown-container\"} style={displayContainer}>\n <DropDownItems\n showScroll={showScroll}\n dropDownRef={dropDownRef}\n onClose={handleClose}\n >\n {children}\n </DropDownItems>\n </div>\n )}\n </>\n );\n}\n"],"names":["DropDownContext","React","DropDownItem","children","className","onClick","title","ref","useRef","dropDownContext","Error","registerItem","useEffect","DropDownItems","dropDownRef","showScroll","onClose","items","setItems","useState","highlightedItem","setHighlightedItem","useCallback","itemRef","prev","handleKeyDown","event","key","index","contextValue","useMemo","DropDown","disabled","buttonLabel","buttonAriaLabel","buttonClassName","buttonIconClassName","stopCloseOnClickSelf","buttonRef","positionIsCalculated","setPositionIsCalculated","showDropDown","setShowDropDown","handleClose","button","dropDown","handle","target","document","displayContainer"],"mappings":"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"}