@crystallize/design-system 1.5.0 → 1.7.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 (43) hide show
  1. package/CHANGELOG.md +22 -0
  2. package/dist/index.css +85 -142
  3. package/dist/index.d.ts +7 -3
  4. package/dist/index.js +1526 -4411
  5. package/dist/index.mjs +1391 -4294
  6. package/package.json +19 -19
  7. package/src/iconography/document.tsx +19 -0
  8. package/src/iconography/folder.tsx +30 -0
  9. package/src/iconography/index.ts +8 -2
  10. package/src/iconography/product.tsx +42 -0
  11. package/src/rich-text-editor/model/crystallize-to-lexical.ts +1 -1
  12. package/src/rich-text-editor/model/lexical-to-crystallize.ts +2 -2
  13. package/src/rich-text-editor/model/to-text.test.ts +97 -0
  14. package/src/rich-text-editor/model/to-text.ts +47 -0
  15. package/src/rich-text-editor/nodes/BaseNodes.ts +0 -3
  16. package/src/rich-text-editor/plugins/ActionsPlugin/index.tsx +14 -3
  17. package/src/rich-text-editor/plugins/CodeActionMenuPlugin/index.tsx +1 -1
  18. package/src/rich-text-editor/plugins/ComponentPickerPlugin/index.tsx +5 -5
  19. package/src/rich-text-editor/plugins/DraggableBlockPlugin/index.tsx +29 -50
  20. package/src/rich-text-editor/plugins/MaxLengthPlugin/index.tsx +34 -23
  21. package/src/rich-text-editor/plugins/ToolbarPlugin/index.tsx +8 -8
  22. package/src/rich-text-editor/rich-text-editor.css +3 -3
  23. package/src/rich-text-editor/rich-text-editor.stories.tsx +9 -1
  24. package/src/rich-text-editor/rich-text-editor.tsx +30 -24
  25. package/src/rich-text-editor/tests/rich-text-editor-basic-rendering.test.tsx +1 -1
  26. package/src/rich-text-editor/tests/rich-text-editor-model-basics.test.tsx +1 -1
  27. package/src/rich-text-editor/tests/rich-text-editor-model-conversions.test.tsx +1 -1
  28. package/src/rich-text-editor/tests/rich-text-editor-text-formats.test.tsx +1 -1
  29. package/src/rich-text-editor/themes/{PlaygroundEditorTheme.css → CrystallizeRTEditorTheme.css} +81 -85
  30. package/src/rich-text-editor/themes/CrystallizeRTEditorTheme.ts +113 -0
  31. package/dist/draggable-block-menu-KKHDNKJA.svg +0 -1
  32. package/src/rich-text-editor/appSettings.ts +0 -28
  33. package/src/rich-text-editor/context/SettingsContext.tsx +0 -71
  34. package/src/rich-text-editor/context/SharedAutocompleteContext.tsx +0 -60
  35. package/src/rich-text-editor/nodes/AutocompleteNode.tsx +0 -96
  36. package/src/rich-text-editor/plugins/AutocompletePlugin/index.tsx +0 -2536
  37. package/src/rich-text-editor/themes/PlaygroundEditorTheme.ts +0 -113
  38. /package/src/rich-text-editor/{model → types}/crystallize-rich-text-types/code.ts +0 -0
  39. /package/src/rich-text-editor/{model → types}/crystallize-rich-text-types/headings.ts +0 -0
  40. /package/src/rich-text-editor/{model → types}/crystallize-rich-text-types/index.ts +0 -0
  41. /package/src/rich-text-editor/{model → types}/crystallize-rich-text-types/link.ts +0 -0
  42. /package/src/rich-text-editor/{model → types}/crystallize-rich-text-types/table.ts +0 -0
  43. /package/src/rich-text-editor/{types.ts → types/types.ts} +0 -0
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@crystallize/design-system",
3
- "version": "1.5.0",
3
+ "version": "1.7.0",
4
4
  "types": "./dist/index.d.ts",
5
5
  "main": "./dist/index.js",
6
6
  "module": "./dist/index.mjs",
@@ -20,23 +20,23 @@
20
20
  }
21
21
  },
22
22
  "dependencies": {
23
- "@lexical/clipboard": "0.8.1",
24
- "@lexical/code": "0.8.1",
25
- "@lexical/file": "0.8.1",
26
- "@lexical/hashtag": "0.8.1",
27
- "@lexical/html": "0.8.1",
28
- "@lexical/link": "0.8.1",
29
- "@lexical/list": "0.8.1",
30
- "@lexical/mark": "0.8.1",
31
- "@lexical/markdown": "0.8.1",
32
- "@lexical/overflow": "0.8.1",
33
- "@lexical/react": "0.8.1",
34
- "@lexical/rich-text": "0.8.1",
35
- "@lexical/selection": "0.8.1",
36
- "@lexical/table": "0.8.1",
37
- "@lexical/text": "0.8.1",
38
- "@lexical/utils": "0.8.1",
39
- "@lexical/yjs": "0.8.1",
23
+ "@lexical/clipboard": "0.9.0",
24
+ "@lexical/code": "0.9.0",
25
+ "@lexical/file": "0.9.0",
26
+ "@lexical/hashtag": "0.9.0",
27
+ "@lexical/html": "0.9.0",
28
+ "@lexical/link": "0.9.0",
29
+ "@lexical/list": "0.9.0",
30
+ "@lexical/mark": "0.9.0",
31
+ "@lexical/markdown": "0.9.0",
32
+ "@lexical/overflow": "0.9.0",
33
+ "@lexical/react": "0.9.0",
34
+ "@lexical/rich-text": "0.9.0",
35
+ "@lexical/selection": "0.9.0",
36
+ "@lexical/table": "0.9.0",
37
+ "@lexical/text": "0.9.0",
38
+ "@lexical/utils": "0.9.0",
39
+ "@lexical/yjs": "0.9.0",
40
40
  "@radix-ui/react-checkbox": "1.0.1",
41
41
  "@radix-ui/react-dialog": "1.0.2",
42
42
  "@radix-ui/react-dropdown-menu": "2.0.1",
@@ -45,7 +45,7 @@
45
45
  "@radix-ui/react-select": "1.1.2",
46
46
  "@radix-ui/react-slider": "^1.1.0",
47
47
  "class-variance-authority": "^0.4.0",
48
- "lexical": "0.8.1",
48
+ "lexical": "0.9.0",
49
49
  "prettier": "2.8.4",
50
50
  "use-debounce": "8.0.4"
51
51
  },
@@ -0,0 +1,19 @@
1
+ import { forwardRef, SVGProps } from 'react';
2
+
3
+ type DocumentProps = SVGProps<SVGSVGElement>;
4
+
5
+ type DocumentRef = SVGSVGElement;
6
+
7
+ export const Document = forwardRef<DocumentRef, DocumentProps>((delegated, ref) => {
8
+ return (
9
+ <svg ref={ref} width="34" height="34" viewBox="0 0 34 34" fill="none" {...delegated}>
10
+ <path d="m27.127 10.355.175.184V31.34l-20.745-.064V2.652h13.282l3.166 3.346 4.357 4.357h-.235Z" fill="#bff6f8" />
11
+ <path
12
+ d="M27.823 15.88a132.896 132.896 0 0 0-.073-3.047c-.02-.5-.041-1-.065-1.5 0-.25-.019-.5-.054-.747l-.006-.019a.354.354 0 0 0-.087-.27 1.343 1.343 0 0 0-.13-.232 11.003 11.003 0 0 0-.829-.925c-.323-.354-.656-.7-.993-1.039-.662-.67-1.338-1.327-1.983-2.015-.476-.506-.954-1.008-1.433-1.507-.457-.439-.89-.9-1.3-1.383a3.636 3.636 0 0 0-.625-.678 1.162 1.162 0 0 0-.358-.186 2.48 2.48 0 0 0-.76-.06c-.314 0-.63-.007-.946-.007H6.56a.393.393 0 0 0-.387.387c0 9.543-.003 19.085-.009 28.627a.4.4 0 0 0 .4.395c6.913.029 13.827.05 20.742.063a.4.4 0 0 0 .4-.4c0-2.572.046-5.146.086-7.72.04-2.572.065-5.158.032-7.738ZM20.516 3.998c.84.886 1.677 1.776 2.526 2.652 1.045 1.077 2.04 2.264 3.12 3.328-1.907-.173-3.912-.038-5.806-.02 0-2.04.014-4.082 0-6.122.055.052.111.106.16.162Zm6.093 26.943a34.23 34.23 0 0 1-5.133-.017l-7.283-.026c-1.966-.008-3.932-.012-5.897-.012-.439.048-.88.066-1.322.051a2.234 2.234 0 0 0-.023-.5 33.236 33.236 0 0 1-.005-4.21c-.004-4.77-.004-9.541 0-14.313V4.757c0-.316-.14-1.806-.274-1.718.265-.04.534-.04.8 0H19.57c-.032 2.44-.007 4.88-.006 7.32a.4.4 0 0 0 .4.399c2.308.121 4.622.088 6.925-.1l.068.061c-.235 4.204-.044 8.472-.046 12.683 0 2.069-.2 4.258 0 6.318.123 1.338.708 1.066-.303 1.218v.003Z"
13
+ fill="#528693"
14
+ />
15
+ </svg>
16
+ );
17
+ });
18
+
19
+ Document.displayName = 'DocumentIcon';
@@ -0,0 +1,30 @@
1
+ import { forwardRef, SVGProps } from 'react';
2
+
3
+ type FolderProps = SVGProps<SVGSVGElement>;
4
+
5
+ type FolderRef = SVGSVGElement;
6
+
7
+ export const Folder = forwardRef<FolderRef, FolderProps>((delegated, ref) => {
8
+ return (
9
+ <svg ref={ref} width="34" height="34" viewBox="0 0 34 34" fill="none" {...delegated}>
10
+ <path
11
+ d="M29.451 12.006c0-4.26-1.3-3.498-3.767-3.498H14.26l-3.148-3.026H3.978c-2.285 0-2.199 1.236-2.199 3.829v16.218c0 2.037.2 3.037 2.174 3.037"
12
+ fill="#bff6f8"
13
+ />
14
+ <path
15
+ d="M30.31 24.858a53.13 53.13 0 0 0 1.844-8.704c.178-1.544.589-4.137-2.56-4.26-3.15-.124-17.992-.063-20.52-.063-2.528 0-3.149 1.73-3.399 3.768s-2.16 12.968-2.16 12.968 20.658 0 22.695-.062c2.037-.062 3.36-1.34 4.1-3.647Z"
16
+ fill="#bff6f8"
17
+ />
18
+ <path
19
+ d="M3.516 29.141a.581.581 0 0 1-.3-.1A1.978 1.978 0 0 1 1.5 27.855a5.648 5.648 0 0 1-.3-2.362V12.451c0-.5-.01-1.004-.02-1.511-.048-1.2-.027-2.401.06-3.598.211-2.26 1.805-2.444 3.559-2.444h3.724a17.764 17.764 0 0 1 2.477 0c.342.055.652.233.871.5l2.046 1.97c.062.058.133.137.208.223.106.13.224.248.353.354a.488.488 0 0 1 .162-.022h9.972a15.821 15.821 0 0 1 3.12.121 2.89 2.89 0 0 1 2.188 3.282c.65.05 1.276.273 1.811.647 1.413 1.065 1.159 2.959.955 4.48l-.03.216a46.22 46.22 0 0 1-1.835 8.253 5.346 5.346 0 0 1-2.951 3.819 6.528 6.528 0 0 1-2.133.357s-.212 0-.318-.008c-4.376.052-8.636.06-12.224.06l-9.678-.009Zm4.207-1.15c4.092 0 8.183-.005 12.274-.016h.38c1.588 0 3.176-.008 4.762-.024a9.645 9.645 0 0 0 1.676-.08c1.647-.311 2.44-1.778 2.999-3.172a48.96 48.96 0 0 0 1.8-8.72l.021-.185c.163-.77.12-1.57-.125-2.317-.413-.9-1.4-1-2.464-1.026-2.966-.072-6.159-.107-9.76-.107-3.368 0-6.735.03-10.094.066a2.44 2.44 0 0 0-2.556 1.547 9.554 9.554 0 0 0-.45 2.212 184.339 184.339 0 0 1-.617 3.822l-.125.742c-.407 2.42-.823 4.84-1.246 7.259h3.525Zm-3.66-21.93c-.786 0-1.315.114-1.531.682a5.51 5.51 0 0 0-.176 2.069c.008.22.016.435.016.639v15.547c0 .434-.006.868.016 1.3.044.825.239 1.273.679 1.51a820.157 820.157 0 0 0 1.656-9.732c.067-.413.117-.845.17-1.284.079-1.175.329-2.332.741-3.434.812-1.843 2.481-2.1 4.163-2.105h2.7c2.354-.006 4.709-.01 7.064-.011h1.784c1.975 0 3.951.007 5.927.032l1.386-.01h.286l-.006-.033c-.131-.769-.268-1.565-.9-1.9a3.324 3.324 0 0 0-1.498-.268c-.2 0-.4.007-.594.013-.178.005-.35.01-.514.012H16.504c-.182 0-.4.017-.628.034-.274.02-.57.043-.853.043-.4.027-.8-.055-1.155-.24A9.295 9.295 0 0 1 12.55 7.67a28.33 28.33 0 0 0-.533-.492 13.702 13.702 0 0 1-1.09-1.067l-.04-.044-6.825-.006Z"
20
+ fill="#528693"
21
+ />
22
+ <path
23
+ d="M31.61 12.13a3.713 3.713 0 0 0-1.91-.63 2.729 2.729 0 0 0-2-3.259 15.839 15.839 0 0 0-3.092-.12h-8.99c-.321 0-.644.005-.966 0-.262 0-.03.116-.193.042-.237-.107-.5-.478-.68-.654l-1.93-1.854c-.3-.289-.458-.5-.864-.56a17.461 17.461 0 0 0-2.463 0H4.798c-1.8 0-3.17.22-3.362 2.264-.157 1.674-.04 3.413-.04 5.097v12.64c-.089.903.008 1.814.285 2.678a1.899 1.899 0 0 0 1.64 1.1c.058.038.124.06.192.063 7.304 0 14.61.034 21.912-.053a6.325 6.325 0 0 0 2.367-.334 5.186 5.186 0 0 0 2.83-3.61.357.357 0 0 0 .007-.085 45.972 45.972 0 0 0 1.827-8.217c.198-1.484.54-3.463-.846-4.508ZM10.936 5.84c-.045-.023-.054-.045 0 0ZM2.187 26.31c-.031-.581-.016-1.167-.016-1.748V9.451c-.1-.93-.042-1.87.174-2.78.35-.922 1.416-.805 2.237-.805H10.962c.04.035.077.073.112.113.49.558 1.088 1.047 1.624 1.56.383.446.808.853 1.27 1.216.607.375 1.825.133 2.531.133 2.976 0 5.952.007 8.928 0a5.983 5.983 0 0 1 2.699.268c.8.423.9 1.446 1.055 2.314-.661-.023-1.328.01-1.914 0-1.975-.025-3.95-.03-5.925-.032-3.85 0-7.696.008-11.548.015-1.689 0-3.23.283-3.98 1.986a19.563 19.563 0 0 0-.9 4.67 793.307 793.307 0 0 1-1.695 9.978c-.715-.24-.982-.809-1.032-1.778ZM31.808 16a50.136 50.136 0 0 1-1.78 8.727.347.347 0 0 0-.03.045c-.599 1.493-1.444 2.973-3.155 3.299a9.703 9.703 0 0 1-1.699.082c-1.714.017-3.43.02-5.144.025-4.432.013-8.864.019-13.294.017H3.959c.436-2.497.865-4.996 1.289-7.497.253-1.514.517-3.025.731-4.544a9.83 9.83 0 0 1 .464-2.268 2.66 2.66 0 0 1 2.74-1.674c6.616-.07 13.25-.12 19.864.041 1.013.025 2.164.1 2.641 1.143.269.842.31 1.74.12 2.604Z"
24
+ fill="#528693"
25
+ />
26
+ </svg>
27
+ );
28
+ });
29
+
30
+ Folder.displayName = 'FolderIcon';
@@ -10,8 +10,10 @@ import { CloudWithKeyHole } from './cloud-with-key-hole';
10
10
  import { Copy } from './copy';
11
11
  import { Crystal } from './crystal';
12
12
  import { Customers } from './customers';
13
+ import { Document } from './document';
13
14
  import { Edit } from './edit';
14
15
  import { Error } from './error';
16
+ import { Folder } from './folder';
15
17
  import { Frontends } from './frontends';
16
18
  import { Fulfilment } from './fulfilment';
17
19
  import { Glasses } from './glasses';
@@ -31,6 +33,7 @@ import { People } from './people';
31
33
  import { Percentage } from './percentage';
32
34
  import { PlansAndPricing } from './plans-and-pricing';
33
35
  import { PriceTag } from './price-tag';
36
+ import { Product } from './product';
34
37
  import { Rocket } from './rocket';
35
38
  import { Shapes } from './shapes';
36
39
  import { StockLocation } from './stock-location';
@@ -58,8 +61,10 @@ export const Icon = {
58
61
  CloudWithKeyHole,
59
62
  Crystal,
60
63
  Customers,
64
+ Document,
61
65
  Edit,
62
66
  Error,
67
+ Folder,
63
68
  Frontends,
64
69
  Fulfilment,
65
70
  Glasses,
@@ -79,15 +84,16 @@ export const Icon = {
79
84
  Percentage,
80
85
  PlansAndPricing,
81
86
  PriceTag,
87
+ Product,
82
88
  Rocket,
83
89
  Shapes,
84
90
  StockLocation,
91
+ SubscriptionContracts,
92
+ SubscriptionPlans,
85
93
  /**
86
94
  * @deprecated Use SubscriptionPlans icon instead
87
95
  */
88
96
  Subscription,
89
- SubscriptionContracts,
90
- SubscriptionPlans,
91
97
  Target,
92
98
  Topics,
93
99
  UsageMeter,
@@ -0,0 +1,42 @@
1
+ import { forwardRef, SVGProps } from 'react';
2
+
3
+ type ProductProps = SVGProps<SVGSVGElement>;
4
+
5
+ type ProductRef = SVGSVGElement;
6
+
7
+ export const Product = forwardRef<ProductRef, ProductProps>((delegated, ref) => {
8
+ return (
9
+ <svg ref={ref} width="34" height="34" viewBox="0 0 34 34" fill="none" {...delegated}>
10
+ <path
11
+ d="M30.14 8.196a5.316 5.316 0 0 0-7.567-.609c-.02-.01-.02-.03-.03-.042a10.505 10.505 0 0 0-10.024-2.067 5.313 5.313 0 0 0-7.902-1.154c-2.887 2.382-2.561 6.759-.1 9.288a.346.346 0 0 0 .272.126 16.462 16.462 0 0 0 .368 11.271c2.392 5.448 8.68 6.728 14.063 5.698 6.559-1.25 9.373-6.717 8.496-12.951a13.94 13.94 0 0 0 2.109-1.628 6.065 6.065 0 0 0 .316-7.932ZM4.754 5.216a4.578 4.578 0 0 1 7.021.524 10.141 10.141 0 0 0-3.478 2.141 13.557 13.557 0 0 0-3.26 5.143c-2.014-2.078-2.445-5.627-.283-7.808Zm14.252 24.747c-5.397.976-11.565-.43-13.476-6.171-1.574-4.733-.631-11.041 2.767-14.766 3.399-3.725 9.817-4.45 13.694-.924.01.01.02.01.032.021a6.367 6.367 0 0 0 .7 8.91 5.19 5.19 0 0 0 4.533.872c.283 5.877-1.867 10.903-8.25 12.058Zm3.831-13.885a5.53 5.53 0 0 1 .357-7.996 4.552 4.552 0 0 1 6.969 1.542c2.183 4.27-3.339 10.473-7.326 6.454Z"
12
+ fill="#528693"
13
+ />
14
+ <path
15
+ d="M15.605 18.271c-.073.441-.2.872-.241 1.323-.036.419-.05.839-.042 1.26-.011.377-.62.482-.683.083a4.85 4.85 0 0 1 .43-2.899c.169-.301.578-.07.536.233ZM10.252 16.939c-.073.44-.2.882-.24 1.332-.036.416-.05.833-.044 1.25-.01.378-.618.493-.681.094-.16-.988-.01-2 .43-2.899.168-.313.578-.082.535.223Z"
16
+ fill="#528693"
17
+ />
18
+ <path
19
+ d="M30.215 8.138a5.198 5.198 0 0 0-4.088-1.95 5.63 5.63 0 0 0-3.538 1.26 10.142 10.142 0 0 0-6.856-2.53c-1.072.001-2.138.15-3.169.44a5.705 5.705 0 0 0-4.538-2.407A5.38 5.38 0 0 0 4.558 4.25a5.734 5.734 0 0 0-2.09 4.198 7.069 7.069 0 0 0 1.97 5.227c.056.07.133.119.22.14a16.514 16.514 0 0 0 .4 11.234c1.699 3.868 5.627 6.087 10.765 6.087 1.144 0 2.285-.11 3.408-.328 6.167-1.17 9.535-6.297 8.556-12.994.02-.021.12-.081.21-.141a10.2 10.2 0 0 0 1.889-1.47 6.152 6.152 0 0 0 .329-8.065ZM4.827 5.288A4.435 4.435 0 0 1 8.005 3.91a4.64 4.64 0 0 1 3.608 1.788 9.881 9.881 0 0 0-3.378 2.108 13.573 13.573 0 0 0-3.237 5.03c-1.79-1.948-2.36-5.339-.171-7.546Zm14.164 24.58c-1.026.186-2.066.28-3.108.279-5.168 0-8.906-2.33-10.256-6.387-1.649-4.947-.49-11.115 2.75-14.663a10.164 10.164 0 0 1 7.436-3.189 9.085 9.085 0 0 1 6.067 2.22 6.248 6.248 0 0 0-1.44 4.557 6.305 6.305 0 0 0 2.22 4.428 5.121 5.121 0 0 0 3.208 1.07 5.43 5.43 0 0 0 1.29-.15c.288 6.626-2.62 10.824-8.167 11.835Zm10.685-15.154a4.934 4.934 0 0 1-3.988 2.559 3.824 3.824 0 0 1-2.779-1.268 5.524 5.524 0 0 1-1.5-4.21 4.955 4.955 0 0 1 1.85-3.638 4.638 4.638 0 0 1 2.849-.99 4.416 4.416 0 0 1 3.968 2.5 5.199 5.199 0 0 1-.401 5.047h.001Z"
20
+ fill="#528693"
21
+ />
22
+ <path
23
+ d="M11.614 5.697a9.882 9.882 0 0 0-3.379 2.108 13.573 13.573 0 0 0-3.237 5.03c-1.79-1.948-2.36-5.338-.17-7.546a4.435 4.435 0 0 1 3.178-1.38 4.64 4.64 0 0 1 3.608 1.788ZM29.675 14.714a4.932 4.932 0 0 1-3.988 2.559 3.824 3.824 0 0 1-2.779-1.268 5.524 5.524 0 0 1-1.5-4.21 4.954 4.954 0 0 1 1.85-3.638 4.638 4.638 0 0 1 2.849-.99 4.416 4.416 0 0 1 3.968 2.5 5.197 5.197 0 0 1-.4 5.047Z"
24
+ fill="#bff6f8"
25
+ />
26
+ <path
27
+ d="M27.156 18.032a5.437 5.437 0 0 1-1.29.15 5.123 5.123 0 0 1-3.208-1.069 6.307 6.307 0 0 1-2.219-4.428 6.248 6.248 0 0 1 1.44-4.557 9.085 9.085 0 0 0-6.067-2.22 10.164 10.164 0 0 0-7.437 3.188c-3.238 3.548-4.398 9.716-2.749 14.663 1.35 4.058 5.088 6.387 10.256 6.387a17.358 17.358 0 0 0 3.11-.278c5.546-1.01 8.454-5.209 8.164-11.835ZM9.625 16.673a.37.37 0 0 1 .32-.21.415.415 0 0 1 .3.15.427.427 0 0 1 .11.34c-.03.17-.07.34-.1.51-.068.27-.114.543-.14.82a6.266 6.266 0 0 0-.04.859l-.01.38a.465.465 0 0 1-.48.44.391.391 0 0 1-.4-.33 4.953 4.953 0 0 1 .44-2.959Zm4.667 7.957a1.698 1.698 0 0 1-1.569.859c-.22.003-.44-.03-.65-.1-.39-.14-.72-.407-.94-.759a1.519 1.519 0 0 1-1.049.43 1.499 1.499 0 0 1-1.379-1.4.357.357 0 0 1 .1-.278.457.457 0 0 1 .34-.14.365.365 0 0 1 .39.32c.04.31.23.669.61.669.27 0 .45-.2.649-.4 0-.19-.02-.31-.02-.42a.4.4 0 0 1 .41-.4.388.388 0 0 1 .384.255.4.4 0 0 1 .026.155 1.207 1.207 0 0 0 .86 1.22c.085.019.172.029.26.03a1.97 1.97 0 0 0 1.099-.48.314.314 0 0 1 .18-.06.326.326 0 0 1 .26.15.4.4 0 0 1 .04.35Zm1.31-5.838a7.647 7.647 0 0 0-.14.81 6.477 6.477 0 0 0-.04.88v.37a.464.464 0 0 1-.48.439.384.384 0 0 1-.4-.34 4.898 4.898 0 0 1 .44-2.959.367.367 0 0 1 .31-.2.434.434 0 0 1 .41.49c-.03.18-.06.341-.1.51Z"
28
+ fill="#bff6f8"
29
+ />
30
+ <path
31
+ d="M15.702 18.282c-.03.18-.06.341-.1.51a7.673 7.673 0 0 0-.14.81 6.493 6.493 0 0 0-.04.88v.37a.464.464 0 0 1-.48.439.384.384 0 0 1-.4-.34 4.898 4.898 0 0 1 .44-2.959.367.367 0 0 1 .31-.2.434.434 0 0 1 .41.49ZM10.354 16.953c-.03.17-.07.34-.1.51a5.63 5.63 0 0 0-.14.82 6.25 6.25 0 0 0-.04.859l-.01.38a.465.465 0 0 1-.48.44.391.391 0 0 1-.4-.33 4.953 4.953 0 0 1 .44-2.959.37.37 0 0 1 .32-.21.415.415 0 0 1 .3.15.425.425 0 0 1 .11.34ZM14.293 24.63a1.699 1.699 0 0 1-1.569.859c-.22.003-.44-.03-.65-.1-.39-.14-.72-.407-.94-.759a1.519 1.519 0 0 1-1.049.43 1.5 1.5 0 0 1-1.38-1.4.357.357 0 0 1 .1-.278.457.457 0 0 1 .34-.14.365.365 0 0 1 .39.32c.04.31.23.669.61.669.27 0 .45-.2.65-.4 0-.19-.02-.31-.02-.42a.4.4 0 0 1 .41-.4.388.388 0 0 1 .384.255c.018.05.027.102.025.155a1.207 1.207 0 0 0 .86 1.22c.085.019.172.029.26.03a1.97 1.97 0 0 0 1.1-.48.316.316 0 0 1 .18-.06.327.327 0 0 1 .26.15.398.398 0 0 1 .04.35Z"
32
+ fill="#528693"
33
+ />
34
+ <path
35
+ d="M14.198 24.588a1.739 1.739 0 0 1-2.088.7c-.415-.15-.76-.45-.966-.84a1.351 1.351 0 0 1-1.144.5 1.372 1.372 0 0 1-1.2-1.3c-.02-.356.579-.44.63-.083a.784.784 0 0 0 .714.755c.346 0 .557-.262.777-.493a2.85 2.85 0 0 1-.052-.42.31.31 0 0 1 .619 0 1.31 1.31 0 0 0 .934 1.322 1.73 1.73 0 0 0 1.448-.461c.213-.14.412.133.328.32Z"
36
+ fill="#528693"
37
+ />
38
+ </svg>
39
+ );
40
+ });
41
+
42
+ Product.displayName = 'ProductIcon';
@@ -13,7 +13,7 @@ import { $createHorizontalRuleNode } from '@lexical/react/LexicalHorizontalRuleN
13
13
  import { $createHeadingNode, $createQuoteNode } from '@lexical/rich-text';
14
14
  import { $createTableCellNode, $createTableNode, $createTableRowNode } from '@lexical/table';
15
15
 
16
- import type { CrystallizeRichTextNode, CrystallizeRichText } from './crystallize-rich-text-types';
16
+ import type { CrystallizeRichTextNode, CrystallizeRichText } from '../types/crystallize-rich-text-types';
17
17
 
18
18
  export function composeInitialState({ richText }: { richText: CrystallizeRichText }) {
19
19
  return function setLexicalState() {
@@ -19,8 +19,8 @@ import type {
19
19
  CrystallizeRichTextNode,
20
20
  CrystallizeRichText,
21
21
  CrystallizeRichTextCodeNodes,
22
- } from './crystallize-rich-text-types';
23
- import type { CrystallizeRichTextHeadingTypes } from './crystallize-rich-text-types/headings';
22
+ } from '../types/crystallize-rich-text-types';
23
+ import type { CrystallizeRichTextHeadingTypes } from '../types/crystallize-rich-text-types/headings';
24
24
 
25
25
  const headingMapper: Record<HeadingTagType, CrystallizeRichTextHeadingTypes> = {
26
26
  h1: 'heading1',
@@ -0,0 +1,97 @@
1
+ /* eslint-disable no-console */
2
+
3
+ import { toText } from './to-text';
4
+
5
+ describe('RichTextEditor toText', () => {
6
+ it('can convert very simple models', async () => {
7
+ expect(
8
+ toText({
9
+ kind: 'block',
10
+ type: 'paragraph',
11
+ textContent: 'Hi there!',
12
+ }),
13
+ ).toBe('Hi there!');
14
+
15
+ expect(
16
+ toText({
17
+ kind: 'block',
18
+ type: 'paragraph',
19
+ textContent: 'Hi \nthere!',
20
+ }),
21
+ ).toBe('Hi \nthere!');
22
+ });
23
+
24
+ it('will trim the start and end new lines of the text', async () => {
25
+ expect(
26
+ toText({
27
+ kind: 'block',
28
+ type: 'paragraph',
29
+ textContent: '\nHi there!\n',
30
+ }),
31
+ ).toBe('Hi there!');
32
+ });
33
+
34
+ it('Will preserve line break nodes if told to', async () => {
35
+ expect(
36
+ toText(
37
+ {
38
+ kind: 'block',
39
+ type: 'paragraph',
40
+ children: [
41
+ {
42
+ kind: 'inline',
43
+ textContent: 'Hi ',
44
+ },
45
+ {
46
+ kind: 'inline',
47
+ type: 'line-break',
48
+ },
49
+ {
50
+ kind: 'inline',
51
+ textContent: 'there!',
52
+ },
53
+ ],
54
+ },
55
+ {
56
+ keepLineBreaks: true,
57
+ },
58
+ ),
59
+ ).toBe('Hi \nthere!');
60
+
61
+ expect(
62
+ toText({
63
+ kind: 'block',
64
+ type: 'paragraph',
65
+ textContent: 'Hi \nthere!',
66
+ }),
67
+ ).toBe('Hi \nthere!');
68
+ });
69
+
70
+ it('Will remove line break nodes if told to', async () => {
71
+ expect(
72
+ toText(
73
+ {
74
+ kind: 'block',
75
+ type: 'paragraph',
76
+ children: [
77
+ {
78
+ kind: 'inline',
79
+ textContent: 'Hi ',
80
+ },
81
+ {
82
+ kind: 'inline',
83
+ type: 'line-break',
84
+ },
85
+ {
86
+ kind: 'inline',
87
+ textContent: 'there!',
88
+ },
89
+ ],
90
+ },
91
+ {
92
+ keepLineBreaks: false,
93
+ },
94
+ ),
95
+ ).toBe('Hi there!');
96
+ });
97
+ });
@@ -0,0 +1,47 @@
1
+ /**
2
+ * This is pretty much a direct copy from:
3
+ * https://github.com/CrystallizeAPI/crystallize-content-transformer/blob/main/src/converters/text/to-text.js
4
+ * I could not/did not want to import it since then original package is not in Typescript
5
+ */
6
+
7
+ import type { CrystallizeRichText, CrystallizeRichTextNode } from '../types/crystallize-rich-text-types';
8
+
9
+ // Remove first and last new lines
10
+ function trim(str: string) {
11
+ if (!str) {
12
+ return '';
13
+ }
14
+
15
+ return str.replace(/^(\r|\n)+/, '').replace(/(\r|\n)+$/, '');
16
+ }
17
+
18
+ export function toText(model: CrystallizeRichText, options?: { keepLineBreaks: boolean }) {
19
+ function getTextFromNode(node: CrystallizeRichTextNode) {
20
+ if (!node) {
21
+ return '';
22
+ }
23
+
24
+ let childrenText = '';
25
+ if (node.children) {
26
+ childrenText = node.children.reduce((acc, n) => acc + getTextFromNode(n), '');
27
+ }
28
+
29
+ let content = '';
30
+
31
+ content += node.textContent || childrenText || '';
32
+
33
+ if (node.kind === 'block') {
34
+ content = `\n${content}\n`;
35
+ } else if (options?.keepLineBreaks && node.type === 'line-break') {
36
+ content += '\n';
37
+ }
38
+
39
+ return content;
40
+ }
41
+
42
+ if (Array.isArray(model)) {
43
+ return model.map(getTextFromNode).join('').trimStart().trimEnd();
44
+ }
45
+
46
+ return trim(getTextFromNode(model));
47
+ }
@@ -17,8 +17,6 @@ import { HorizontalRuleNode } from '@lexical/react/LexicalHorizontalRuleNode';
17
17
  import { HeadingNode, QuoteNode } from '@lexical/rich-text';
18
18
  import { TableCellNode, TableNode, TableRowNode } from '@lexical/table';
19
19
 
20
- // import { AutocompleteNode } from './AutocompleteNode';
21
-
22
20
  import { KeywordNode } from './KeywordNode';
23
21
  import { TableNode as NewTableNode } from './TableNode';
24
22
 
@@ -37,7 +35,6 @@ export const BaseNodes: Array<Klass<LexicalNode>> = [
37
35
  AutoLinkNode,
38
36
  LinkNode,
39
37
  OverflowNode,
40
- // AutocompleteNode,
41
38
  KeywordNode,
42
39
  HorizontalRuleNode,
43
40
  MarkNode,
@@ -12,9 +12,19 @@ import { useLexicalComposerContext } from '@lexical/react/LexicalComposerContext
12
12
 
13
13
  import { ActionMenu } from '../../../action-menu';
14
14
  import { lexicalToCrystallizeRichText } from '../../model/lexical-to-crystallize';
15
- import type { CrystallizeRichTextActionMenuItem } from '../../types';
15
+ import type { CrystallizeRichTextActionMenuItem } from '../../types/types';
16
16
 
17
- async function exportFile(editor: LexicalEditor) {
17
+ async function copyJson(editor: LexicalEditor) {
18
+ const json = lexicalToCrystallizeRichText({ editorState: editor.getEditorState() });
19
+
20
+ try {
21
+ await navigator.clipboard.writeText(JSON.stringify(json, null, 1));
22
+ } catch (error) {
23
+ console.warn('Copy failed', error);
24
+ }
25
+ }
26
+
27
+ async function exportJson(editor: LexicalEditor) {
18
28
  const json = lexicalToCrystallizeRichText({ editorState: editor.getEditorState() });
19
29
 
20
30
  const blob = new Blob([JSON.stringify(json, null, 1)], {
@@ -56,7 +66,8 @@ export default function ActionsPlugin({
56
66
  {actionItem.title}
57
67
  </ActionMenu.Item>
58
68
  ))}
59
- <ActionMenu.Item onSelect={() => exportFile(editor)}>Export to JSON</ActionMenu.Item>
69
+ <ActionMenu.Item onSelect={() => copyJson(editor)}>Copy JSON</ActionMenu.Item>
70
+ <ActionMenu.Item onSelect={() => exportJson(editor)}>Export JSON</ActionMenu.Item>
60
71
  <ActionMenu.Item
61
72
  className="danger"
62
73
  onSelect={() => {
@@ -137,7 +137,7 @@ function getMouseInfo(event: MouseEvent): {
137
137
  const target = event.target;
138
138
 
139
139
  if (target && target instanceof HTMLElement) {
140
- const codeDOMNode = target.closest<HTMLElement>('code.PlaygroundEditorTheme__code');
140
+ const codeDOMNode = target.closest<HTMLElement>('code.CrystallizeRTEditorTheme__code');
141
141
  const isOutside = !(codeDOMNode || target.closest<HTMLElement>('div.code-action-menu-container'));
142
142
 
143
143
  return { codeDOMNode, isOutside };
@@ -20,7 +20,7 @@ import {
20
20
  useBasicTypeaheadTriggerMatch,
21
21
  } from '@lexical/react/LexicalTypeaheadMenuPlugin';
22
22
  import { $createHeadingNode, $createQuoteNode } from '@lexical/rich-text';
23
- import { $setBlocksType_experimental } from '@lexical/selection';
23
+ import { $setBlocksType } from '@lexical/selection';
24
24
  import { INSERT_TABLE_COMMAND } from '@lexical/table';
25
25
 
26
26
  // import { InsertNewTableDialog } from '../TablePlugin';
@@ -152,7 +152,7 @@ export default function ComponentPickerMenuPlugin(): JSX.Element {
152
152
  editor.update(() => {
153
153
  const selection = $getSelection();
154
154
  if ($isRangeSelection(selection)) {
155
- $setBlocksType_experimental(selection, () => $createParagraphNode());
155
+ $setBlocksType(selection, () => $createParagraphNode());
156
156
  }
157
157
  }),
158
158
  }),
@@ -165,7 +165,7 @@ export default function ComponentPickerMenuPlugin(): JSX.Element {
165
165
  editor.update(() => {
166
166
  const selection = $getSelection();
167
167
  if ($isRangeSelection(selection)) {
168
- $setBlocksType_experimental(selection, () =>
168
+ $setBlocksType(selection, () =>
169
169
  // @ts-ignore Correct types, but since they're dynamic TS doesn't like it.
170
170
  $createHeadingNode(`h${n}`),
171
171
  );
@@ -207,7 +207,7 @@ export default function ComponentPickerMenuPlugin(): JSX.Element {
207
207
  editor.update(() => {
208
208
  const selection = $getSelection();
209
209
  if ($isRangeSelection(selection)) {
210
- $setBlocksType_experimental(selection, () => $createQuoteNode());
210
+ $setBlocksType(selection, () => $createQuoteNode());
211
211
  }
212
212
  }),
213
213
  }),
@@ -220,7 +220,7 @@ export default function ComponentPickerMenuPlugin(): JSX.Element {
220
220
 
221
221
  if ($isRangeSelection(selection)) {
222
222
  if (selection.isCollapsed()) {
223
- $setBlocksType_experimental(selection, () => $createCodeNode());
223
+ $setBlocksType(selection, () => $createCodeNode());
224
224
  } else {
225
225
  // Will this ever happen?
226
226
  const textContent = selection.getTextContent();