@alpaca-editor/core 1.0.3996 → 1.0.4000

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 (50) hide show
  1. package/dist/editor/field-types/InternalLinkFieldEditor.js +29 -9
  2. package/dist/editor/field-types/InternalLinkFieldEditor.js.map +1 -1
  3. package/dist/editor/field-types/TreeListEditor.js +20 -12
  4. package/dist/editor/field-types/TreeListEditor.js.map +1 -1
  5. package/dist/editor/field-types/richtext/components/ReactSlate.d.ts +3 -3
  6. package/dist/editor/field-types/richtext/components/ReactSlate.js +195 -172
  7. package/dist/editor/field-types/richtext/components/ReactSlate.js.map +1 -1
  8. package/dist/editor/page-editor-chrome/PlaceholderDropZone.js +1 -1
  9. package/dist/editor/page-editor-chrome/PlaceholderDropZone.js.map +1 -1
  10. package/dist/editor/sidebar/MainContentTree.js +1 -1
  11. package/dist/editor/sidebar/MainContentTree.js.map +1 -1
  12. package/dist/editor/utils.d.ts +1 -0
  13. package/dist/editor/utils.js +3 -0
  14. package/dist/editor/utils.js.map +1 -1
  15. package/dist/editor/views/CompareView.js.map +1 -1
  16. package/dist/page-wizard/PageWizard.d.ts +5 -1
  17. package/dist/page-wizard/PageWizard.js.map +1 -1
  18. package/dist/page-wizard/WizardSteps.js +1 -0
  19. package/dist/page-wizard/WizardSteps.js.map +1 -1
  20. package/dist/page-wizard/steps/ComponentTypesSelector.d.ts +2 -1
  21. package/dist/page-wizard/steps/ComponentTypesSelector.js +27 -90
  22. package/dist/page-wizard/steps/ComponentTypesSelector.js.map +1 -1
  23. package/dist/page-wizard/steps/ContentStep.js +63 -11
  24. package/dist/page-wizard/steps/ContentStep.js.map +1 -1
  25. package/dist/page-wizard/steps/schema.js +4 -4
  26. package/dist/page-wizard/steps/schema.js.map +1 -1
  27. package/dist/page-wizard/steps/usePageCreator.d.ts +2 -1
  28. package/dist/page-wizard/steps/usePageCreator.js +62 -8
  29. package/dist/page-wizard/steps/usePageCreator.js.map +1 -1
  30. package/dist/page-wizard/usePageWizard.js +2 -0
  31. package/dist/page-wizard/usePageWizard.js.map +1 -1
  32. package/dist/revision.d.ts +2 -2
  33. package/dist/revision.js +2 -2
  34. package/dist/styles.css +3 -3
  35. package/package.json +1 -1
  36. package/src/editor/field-types/InternalLinkFieldEditor.tsx +99 -73
  37. package/src/editor/field-types/TreeListEditor.tsx +39 -32
  38. package/src/editor/field-types/richtext/components/ReactSlate.tsx +532 -446
  39. package/src/editor/page-editor-chrome/PlaceholderDropZone.tsx +1 -1
  40. package/src/editor/sidebar/MainContentTree.tsx +1 -0
  41. package/src/editor/utils.ts +4 -0
  42. package/src/editor/views/CompareView.tsx +1 -1
  43. package/src/page-wizard/PageWizard.tsx +5 -1
  44. package/src/page-wizard/WizardSteps.tsx +1 -0
  45. package/src/page-wizard/steps/ComponentTypesSelector.tsx +34 -115
  46. package/src/page-wizard/steps/ContentStep.tsx +83 -16
  47. package/src/page-wizard/steps/schema.ts +4 -4
  48. package/src/page-wizard/steps/usePageCreator.ts +84 -9
  49. package/src/page-wizard/usePageWizard.ts +2 -0
  50. package/src/revision.ts +2 -2
@@ -1,33 +1,35 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
- import React, { useCallback, useMemo, useState, forwardRef, useRef, useEffect } from 'react';
3
- import { createEditor, Editor, Element, Transforms } from 'slate';
4
- import { Slate, Editable, withReact, ReactEditor } from 'slate-react';
5
- import { withHistory } from 'slate-history';
6
- import isEqual from 'lodash/isEqual';
7
- import './ReactSlate.css';
8
- import { SLATE_MARKS, SLATE_BLOCKS, SLATE_ALIGNMENTS } from '../types';
9
- import EditorDropdown from './EditorDropdown';
10
- import { ToolbarButton } from './ToolbarButton';
11
- import { LinkEditorDialog } from '../../../LinkEditorDialog';
12
- import { htmlToSlate, slateToHtml } from '../utils/conversion';
13
- import { createPluginsFromConfig } from '../config/pluginFactory';
14
- import { useCachedSimplifiedProfile } from '../hooks/useProfileCache';
15
- import { classNames } from 'primereact/utils';
2
+ import React, { useCallback, useMemo, useState, forwardRef, useRef, useEffect, } from "react";
3
+ import { createEditor, Editor, Element, Transforms } from "slate";
4
+ import { Slate, Editable, withReact, ReactEditor } from "slate-react";
5
+ import { withHistory } from "slate-history";
6
+ import isEqual from "lodash/isEqual";
7
+ import "./ReactSlate.css";
8
+ import { SLATE_MARKS, SLATE_BLOCKS, SLATE_ALIGNMENTS, } from "../types";
9
+ import EditorDropdown from "./EditorDropdown";
10
+ import { ToolbarButton } from "./ToolbarButton";
11
+ import { LinkEditorDialog } from "../../../LinkEditorDialog";
12
+ import { htmlToSlate, slateToHtml } from "../utils/conversion";
13
+ import { createPluginsFromConfig } from "../config/pluginFactory";
14
+ import { useCachedSimplifiedProfile } from "../hooks/useProfileCache";
15
+ import { classNames } from "primereact/utils";
16
16
  // Helper function to normalize HTML for comparison
17
17
  const normalizeHtmlForComparison = (html) => {
18
18
  if (!html)
19
- return '';
19
+ return "";
20
20
  // Create a temporary DOM element to normalize the HTML
21
- const temp = document.createElement('div');
21
+ const temp = document.createElement("div");
22
22
  temp.innerHTML = html;
23
23
  // Remove extra whitespace and normalize structure
24
24
  const normalizedHtml = temp.innerHTML
25
- .replace(/\s+/g, ' ') // Replace multiple spaces with single space
26
- .replace(/>\s+</g, '><') // Remove spaces between tags
25
+ .replace(/\s+/g, " ") // Replace multiple spaces with single space
26
+ .replace(/>\s+</g, "><") // Remove spaces between tags
27
27
  .trim();
28
28
  // Handle common empty content patterns
29
- if (normalizedHtml === '<p><br></p>' || normalizedHtml === '<br>' || normalizedHtml === '<p></p>') {
30
- return '';
29
+ if (normalizedHtml === "<p><br></p>" ||
30
+ normalizedHtml === "<br>" ||
31
+ normalizedHtml === "<p></p>") {
32
+ return "";
31
33
  }
32
34
  return normalizedHtml;
33
35
  };
@@ -49,13 +51,13 @@ const isHtmlConversionStable = (originalHtml, slateValue, profile) => {
49
51
  return normalizedOriginal === normalizedConverted;
50
52
  }
51
53
  catch (error) {
52
- console.warn('HTML conversion stability check failed:', error);
54
+ console.warn("HTML conversion stability check failed:", error);
53
55
  // If we can't check stability, assume it's not stable to be safe
54
56
  return false;
55
57
  }
56
58
  };
57
59
  export const ReactSlate = forwardRef((props, ref) => {
58
- const { value = '', onChange, onFocus, onBlur, readOnly = false, placeholder = 'Enter some text...', profile } = props;
60
+ const { value = "", onChange, onFocus, onBlur, readOnly = false, placeholder = "Enter some text...", profile, } = props;
59
61
  // Create the Slate editor with plugins
60
62
  const editor = useMemo(() => {
61
63
  // Start with base editor
@@ -68,8 +70,8 @@ export const ReactSlate = forwardRef((props, ref) => {
68
70
  }, []);
69
71
  const editorProfile = profile || {
70
72
  toolbar: {
71
- groups: []
72
- }
73
+ groups: [],
74
+ },
73
75
  };
74
76
  // Convert to simplified profile for the conversion functions (with caching)
75
77
  const simplifiedProfile = useCachedSimplifiedProfile(editorProfile);
@@ -93,7 +95,7 @@ export const ReactSlate = forwardRef((props, ref) => {
93
95
  if (!isEqual(newValue, internalValue)) {
94
96
  setInternalValue(newValue);
95
97
  // Force remount by incrementing the key
96
- setRemountKey(prev => prev + 1);
98
+ setRemountKey((prev) => prev + 1);
97
99
  }
98
100
  }, [value, simplifiedProfile]);
99
101
  // Handle value changes with round-trip validation
@@ -125,66 +127,72 @@ export const ReactSlate = forwardRef((props, ref) => {
125
127
  }, [onChange, simplifiedProfile]);
126
128
  const getOption = (type, id) => {
127
129
  switch (type) {
128
- case 'mark':
130
+ case "mark":
129
131
  const markConfig = SLATE_MARKS[id];
130
- return markConfig ? {
131
- id,
132
- label: markConfig.label,
133
- icon: markConfig.icon,
134
- isActive: (editor) => editor.isMarkActive(id),
135
- toggle: (editor, event) => {
136
- event.preventDefault();
137
- editor.toggleMark(id);
132
+ return markConfig
133
+ ? {
134
+ id,
135
+ label: markConfig.label,
136
+ icon: markConfig.icon,
137
+ isActive: (editor) => editor.isMarkActive(id),
138
+ toggle: (editor, event) => {
139
+ event.preventDefault();
140
+ editor.toggleMark(id);
141
+ },
138
142
  }
139
- } : undefined;
140
- case 'block':
143
+ : undefined;
144
+ case "block":
141
145
  const blockConfig = SLATE_BLOCKS[id];
142
- return blockConfig ? {
143
- id,
144
- label: blockConfig.label,
145
- icon: blockConfig.icon,
146
- isActive: (editor) => editor.isBlockActive(id),
147
- toggle: (editor, event) => {
148
- event.preventDefault();
149
- editor.toggleBlock(id);
146
+ return blockConfig
147
+ ? {
148
+ id,
149
+ label: blockConfig.label,
150
+ icon: blockConfig.icon,
151
+ isActive: (editor) => editor.isBlockActive(id),
152
+ toggle: (editor, event) => {
153
+ event.preventDefault();
154
+ editor.toggleBlock(id);
155
+ },
150
156
  }
151
- } : undefined;
152
- case 'alignment':
157
+ : undefined;
158
+ case "alignment":
153
159
  const alignConfig = SLATE_ALIGNMENTS[id];
154
- return alignConfig ? {
155
- id,
156
- label: alignConfig.label,
157
- icon: alignConfig.icon,
158
- isActive: (editor) => editor.isAlignActive(alignConfig.value),
159
- toggle: (editor, event) => {
160
- event.preventDefault();
161
- editor.toggleAlign(alignConfig.value);
160
+ return alignConfig
161
+ ? {
162
+ id,
163
+ label: alignConfig.label,
164
+ icon: alignConfig.icon,
165
+ isActive: (editor) => editor.isAlignActive(alignConfig.value),
166
+ toggle: (editor, event) => {
167
+ event.preventDefault();
168
+ editor.toggleAlign(alignConfig.value);
169
+ },
162
170
  }
163
- } : undefined;
164
- case 'link':
171
+ : undefined;
172
+ case "link":
165
173
  return {
166
- id: 'link',
167
- label: 'Link',
168
- icon: '🔗',
174
+ id: "link",
175
+ label: "Link",
176
+ icon: "🔗",
169
177
  isActive: (editor) => editor.isLinkActive(),
170
178
  toggle: (editor, event) => {
171
179
  event.preventDefault();
172
180
  handleLinkButtonClick();
173
- }
181
+ },
174
182
  };
175
- case 'list':
183
+ case "list":
176
184
  return {
177
185
  id,
178
- label: id === 'unordered-list' ? 'Bulleted List' : 'Numbered List',
179
- icon: id === 'unordered-list' ? '' : '1.',
180
- isActive: (editor) => editor.isListActive(id === 'unordered-list' ? 'unordered' : 'ordered'),
186
+ label: id === "unordered-list" ? "Bulleted List" : "Numbered List",
187
+ icon: id === "unordered-list" ? "" : "1.",
188
+ isActive: (editor) => editor.isListActive(id === "unordered-list" ? "unordered" : "ordered"),
181
189
  toggle: (editor, event) => {
182
190
  event.preventDefault();
183
- editor.toggleList(id === 'unordered-list' ? 'unordered' : 'ordered');
184
- }
191
+ editor.toggleList(id === "unordered-list" ? "unordered" : "ordered");
192
+ },
185
193
  };
186
- case 'divider':
187
- return { id: 'divider', label: 'Divider' };
194
+ case "divider":
195
+ return { id: "divider", label: "Divider" };
188
196
  default:
189
197
  return undefined;
190
198
  }
@@ -192,11 +200,11 @@ export const ReactSlate = forwardRef((props, ref) => {
192
200
  const optionHandlers = {
193
201
  mark: {
194
202
  isActive: (id) => editor.isMarkActive(id),
195
- toggle: (id) => editor.toggleMark(id)
203
+ toggle: (id) => editor.toggleMark(id),
196
204
  },
197
205
  block: {
198
206
  isActive: (id) => editor.isBlockActive(id),
199
- toggle: (id) => editor.toggleBlock(id)
207
+ toggle: (id) => editor.toggleBlock(id),
200
208
  },
201
209
  alignment: {
202
210
  isActive: (id) => {
@@ -208,22 +216,22 @@ export const ReactSlate = forwardRef((props, ref) => {
208
216
  if (alignConfig) {
209
217
  editor.toggleAlign(alignConfig.value);
210
218
  }
211
- }
219
+ },
212
220
  },
213
221
  link: {
214
222
  isActive: () => editor.isLinkActive(),
215
- toggle: () => handleLinkButtonClick()
223
+ toggle: () => handleLinkButtonClick(),
216
224
  },
217
225
  list: {
218
226
  isActive: (id) => {
219
- const listType = id === 'unordered-list' ? 'unordered' : 'ordered';
227
+ const listType = id === "unordered-list" ? "unordered" : "ordered";
220
228
  return editor.isListActive(listType);
221
229
  },
222
230
  toggle: (id, event) => {
223
- const listType = id === 'unordered-list' ? 'unordered' : 'ordered';
231
+ const listType = id === "unordered-list" ? "unordered" : "ordered";
224
232
  editor.toggleList(listType);
225
- }
226
- }
233
+ },
234
+ },
227
235
  };
228
236
  const isOptionActive = (type, id) => {
229
237
  const handler = optionHandlers[type];
@@ -239,7 +247,7 @@ export const ReactSlate = forwardRef((props, ref) => {
239
247
  };
240
248
  const createDropdownOptions = (options) => {
241
249
  return options
242
- .map(option => {
250
+ .map((option) => {
243
251
  const optionObj = getOption(option.type, option.id);
244
252
  if (!optionObj)
245
253
  return null;
@@ -249,7 +257,7 @@ export const ReactSlate = forwardRef((props, ref) => {
249
257
  icon: optionObj.icon,
250
258
  style: optionObj.style,
251
259
  isActive: (editor) => isOptionActive(option.type, option.id),
252
- onSelect: (editor, event) => handleOptionSelect(option.type, option.id)(event)
260
+ onSelect: (editor, event) => handleOptionSelect(option.type, option.id)(event),
253
261
  };
254
262
  })
255
263
  .filter(Boolean);
@@ -258,8 +266,8 @@ export const ReactSlate = forwardRef((props, ref) => {
258
266
  const splitOptionsByDividers = (options) => {
259
267
  const subGroups = [];
260
268
  let currentGroup = [];
261
- options.forEach(option => {
262
- if (option.type === 'divider') {
269
+ options.forEach((option) => {
270
+ if (option.type === "divider") {
263
271
  if (currentGroup.length > 0) {
264
272
  subGroups.push(currentGroup);
265
273
  currentGroup = [];
@@ -276,66 +284,72 @@ export const ReactSlate = forwardRef((props, ref) => {
276
284
  return subGroups;
277
285
  };
278
286
  const renderToolbarGroup = (group, index) => {
279
- const validOptions = group.options.filter(option => getOption(option.type, option.id) || option.type === 'divider');
287
+ const validOptions = group.options.filter((option) => getOption(option.type, option.id) || option.type === "divider");
280
288
  if (validOptions.length === 0)
281
289
  return null;
282
290
  const groupStyle = {
283
- display: 'flex',
284
- alignItems: 'center',
285
- gap: '8px',
286
- flexWrap: 'wrap'
291
+ display: "flex",
292
+ alignItems: "center",
293
+ gap: "8px",
294
+ flexWrap: "wrap",
287
295
  };
288
- return (_jsx("div", { style: groupStyle, children: group.display === 'buttons' ? ((() => {
289
- const subGroups = splitOptionsByDividers(validOptions);
290
- return subGroups.map((subGroup, subGroupIndex) => (_jsx("div", { className: "toolbar-button-group", children: subGroup.map((option, optionIndex) => {
291
- const optionObj = getOption(option.type, option.id);
292
- if (!optionObj)
293
- return null;
294
- return (_jsx(ToolbarButton, { icon: optionObj.icon, active: isOptionActive(option.type, option.id), onMouseDown: handleOptionSelect(option.type, option.id) }, `${option.type}-${option.id}`));
295
- }) }, `subgroup-${subGroupIndex}`)));
296
- })()) : ((() => {
297
- const dropdownOptions = createDropdownOptions(validOptions);
298
- const blockOptions = validOptions.filter(option => option.type === 'block');
299
- // If there's only one block option, render it as a disabled-style button
300
- if (blockOptions.length === 1) {
301
- const singleOption = dropdownOptions.find(opt => blockOptions.some(blockOpt => blockOpt.type === 'block' &&
302
- getOption(blockOpt.type, blockOpt.id) === opt.value));
303
- return (_jsx("div", { className: "toolbar-dropdown-container", children: _jsx("button", { className: "toolbar-dropdown-button", disabled: true, children: group.label ? (_jsxs(_Fragment, { children: [_jsxs("span", { className: "toolbar-dropdown-content", children: [group.label, ": ", singleOption?.label] }), _jsx("span", { className: "toolbar-dropdown-arrow", children: "\u25BC" })] })) : group.showIconsOnly ? (_jsxs(_Fragment, { children: [_jsx("span", { className: "toolbar-dropdown-icon", children: singleOption?.icon }), _jsx("span", { className: "toolbar-dropdown-arrow", children: "\u25BC" })] })) : (_jsxs(_Fragment, { children: [_jsxs("span", { className: "toolbar-dropdown-icon", children: [singleOption?.icon && (_jsx("span", { className: "toolbar-dropdown-icon", children: singleOption.icon })), _jsx("span", { className: "toolbar-dropdown-content", children: singleOption?.label })] }), _jsx("span", { className: "toolbar-dropdown-arrow", children: "\u25BC" })] })) }) }));
304
- }
305
- // Multiple options - render normally wrapped in grey container
306
- const isActive = dropdownOptions.some(option => option.isActive(editor));
307
- return (_jsx("div", { className: "toolbar-dropdown-container", children: _jsx(EditorDropdown, { options: dropdownOptions, editor: editor, label: group.label, buttonStyle: {
308
- padding: '5px 10px',
309
- margin: '0',
310
- background: isActive ? '#ffffff' : 'transparent',
311
- border: 'none',
312
- borderRadius: '3px',
313
- cursor: 'pointer',
314
- boxShadow: isActive ? '0 1px 2px rgba(0,0,0,0.1)' : 'none'
315
- } }) }));
316
- })()) }, `group-${group.id || index}`));
296
+ return (_jsx("div", { style: groupStyle, children: group.display === "buttons"
297
+ ? (() => {
298
+ const subGroups = splitOptionsByDividers(validOptions);
299
+ return subGroups.map((subGroup, subGroupIndex) => (_jsx("div", { className: "toolbar-button-group", children: subGroup.map((option, optionIndex) => {
300
+ const optionObj = getOption(option.type, option.id);
301
+ if (!optionObj)
302
+ return null;
303
+ return (_jsx(ToolbarButton, { icon: optionObj.icon, active: isOptionActive(option.type, option.id), onMouseDown: handleOptionSelect(option.type, option.id) }, `${option.type}-${option.id}`));
304
+ }) }, `subgroup-${subGroupIndex}`)));
305
+ })()
306
+ : (() => {
307
+ const dropdownOptions = createDropdownOptions(validOptions);
308
+ const blockOptions = validOptions.filter((option) => option.type === "block");
309
+ // If there's only one block option, render it as a disabled-style button
310
+ if (blockOptions.length === 1) {
311
+ const singleOption = dropdownOptions.find((opt) => blockOptions.some((blockOpt) => blockOpt.type === "block" &&
312
+ getOption(blockOpt.type, blockOpt.id) === opt.value));
313
+ return (_jsx("div", { className: "toolbar-dropdown-container", children: _jsx("button", { className: "toolbar-dropdown-button", disabled: true, children: group.label ? (_jsxs(_Fragment, { children: [_jsxs("span", { className: "toolbar-dropdown-content", children: [group.label, ": ", singleOption?.label] }), _jsx("span", { className: "toolbar-dropdown-arrow", children: "\u25BC" })] })) : group.showIconsOnly ? (_jsxs(_Fragment, { children: [_jsx("span", { className: "toolbar-dropdown-icon", children: singleOption?.icon }), _jsx("span", { className: "toolbar-dropdown-arrow", children: "\u25BC" })] })) : (_jsxs(_Fragment, { children: [_jsxs("span", { className: "toolbar-dropdown-icon", children: [singleOption?.icon && (_jsx("span", { className: "toolbar-dropdown-icon", children: singleOption.icon })), _jsx("span", { className: "toolbar-dropdown-content", children: singleOption?.label })] }), _jsx("span", { className: "toolbar-dropdown-arrow", children: "\u25BC" })] })) }) }));
314
+ }
315
+ // Multiple options - render normally wrapped in grey container
316
+ const isActive = dropdownOptions.some((option) => option.isActive(editor));
317
+ return (_jsx("div", { className: "toolbar-dropdown-container", children: _jsx(EditorDropdown, { options: dropdownOptions, editor: editor, label: group.label, buttonStyle: {
318
+ padding: "5px 10px",
319
+ margin: "0",
320
+ background: isActive ? "#ffffff" : "transparent",
321
+ border: "none",
322
+ borderRadius: "3px",
323
+ cursor: "pointer",
324
+ boxShadow: isActive
325
+ ? "0 1px 2px rgba(0,0,0,0.1)"
326
+ : "none",
327
+ } }) }));
328
+ })() }, `group-${group.id || index}`));
317
329
  };
318
330
  const [showLinkDialog, setShowLinkDialog] = useState(false);
319
331
  const [selectedLink, setSelectedLink] = useState(null);
320
332
  const [linkDialogCallback, setLinkDialogCallback] = useState(null);
321
333
  const editLink = useCallback((element) => {
322
- const linkType = element.link?.type || 'external';
334
+ const linkType = element.link?.type || "external";
323
335
  let linkData;
324
- if (linkType === 'internal') {
336
+ if (linkType === "internal") {
325
337
  linkData = {
326
- type: 'internal',
327
- itemId: element.link?.itemId || element.link?.targetItemLongId?.split("/").pop() || '',
328
- targetItemLongId: element.link?.targetItemLongId || '',
329
- target: element.link?.target || '',
330
- queryString: element.link?.queryString || ''
338
+ type: "internal",
339
+ itemId: element.link?.itemId ||
340
+ element.link?.targetItemLongId?.split("/").pop() ||
341
+ "",
342
+ targetItemLongId: element.link?.targetItemLongId || "",
343
+ target: element.link?.target || "",
344
+ queryString: element.link?.queryString || "",
331
345
  };
332
346
  }
333
347
  else {
334
348
  linkData = {
335
- type: 'external',
336
- url: element.url || element.link?.url || '',
337
- target: element.link?.target || '_blank',
338
- queryString: element.link?.queryString || ''
349
+ type: "external",
350
+ url: element.url || element.link?.url || "",
351
+ target: element.link?.target || "_blank",
352
+ queryString: element.link?.queryString || "",
339
353
  };
340
354
  }
341
355
  setSelectedLink(linkData);
@@ -348,32 +362,32 @@ export const ReactSlate = forwardRef((props, ref) => {
348
362
  }
349
363
  else {
350
364
  const [linkNode] = Editor.nodes(editor, {
351
- match: n => !Editor.isEditor(n) && Element.isElement(n) && n.type === 'link'
365
+ match: (n) => !Editor.isEditor(n) && Element.isElement(n) && n.type === "link",
352
366
  });
353
367
  if (linkNode) {
354
368
  const [node, path] = linkNode;
355
369
  let newProperties;
356
- if (link.type === 'internal') {
370
+ if (link.type === "internal") {
357
371
  newProperties = {
358
- url: '',
372
+ url: "",
359
373
  link: {
360
- type: 'internal',
374
+ type: "internal",
361
375
  targetItemLongId: link.targetItemLongId,
362
376
  itemId: link.itemId,
363
377
  target: link.target,
364
- queryString: link.queryString
365
- }
378
+ queryString: link.queryString,
379
+ },
366
380
  };
367
381
  }
368
382
  else {
369
383
  newProperties = {
370
384
  url: link.url,
371
385
  link: {
372
- type: 'external',
386
+ type: "external",
373
387
  url: link.url,
374
388
  target: link.target,
375
- queryString: link.queryString
376
- }
389
+ queryString: link.queryString,
390
+ },
377
391
  };
378
392
  }
379
393
  Transforms.setNodes(editor, newProperties, { at: path });
@@ -392,32 +406,34 @@ export const ReactSlate = forwardRef((props, ref) => {
392
406
  editor.insertLink({
393
407
  onOpenLinkDialog: (callback) => {
394
408
  setSelectedLink({
395
- type: 'external',
396
- url: '',
397
- target: '_blank'
409
+ type: "external",
410
+ url: "",
411
+ target: "_blank",
398
412
  });
399
413
  setShowLinkDialog(true);
400
414
  setLinkDialogCallback(() => callback);
401
- }
415
+ },
402
416
  });
403
417
  }, [editor]);
404
418
  const handleKeyDown = useCallback((event) => {
405
- if (event.key === 'Enter' && event.shiftKey) {
419
+ if (event.key === "Enter" && event.shiftKey) {
406
420
  // Handle Shift+Enter for line breaks in all block types
407
421
  event.preventDefault();
408
422
  if (editor.selection) {
409
423
  // Insert literal <br> text
410
- editor.insertText('<br>');
424
+ editor.insertText("<br>");
411
425
  }
412
426
  }
413
- else if (event.key === 'Tab') {
427
+ else if (event.key === "Tab") {
414
428
  event.preventDefault();
415
429
  // Check if we're in a list item more explicitly
416
430
  if (editor.selection) {
417
431
  // Try to find the closest list item ancestor using Editor.above
418
432
  const listItem = Editor.above(editor, {
419
433
  at: editor.selection,
420
- match: n => !Editor.isEditor(n) && Element.isElement(n) && n.type === 'list-item'
434
+ match: (n) => !Editor.isEditor(n) &&
435
+ Element.isElement(n) &&
436
+ n.type === "list-item",
421
437
  });
422
438
  if (listItem) {
423
439
  if (event.shiftKey) {
@@ -431,23 +447,28 @@ export const ReactSlate = forwardRef((props, ref) => {
431
447
  }
432
448
  }
433
449
  }
434
- else if (event.key === 'Backspace' || event.key === 'Delete') {
450
+ else if (event.key === "Backspace" || event.key === "Delete") {
435
451
  // Handle empty list items
436
452
  if (editor.selection) {
437
453
  const listItem = Editor.above(editor, {
438
454
  at: editor.selection,
439
- match: n => !Editor.isEditor(n) && Element.isElement(n) && n.type === 'list-item'
455
+ match: (n) => !Editor.isEditor(n) &&
456
+ Element.isElement(n) &&
457
+ n.type === "list-item",
440
458
  });
441
459
  if (listItem) {
442
460
  const selectedText = Editor.string(editor, editor.selection);
443
461
  const [node, path] = listItem;
444
462
  const nodeText = Editor.string(editor, path);
445
463
  // If the list item is empty or only contains whitespace, convert to paragraph
446
- if (!nodeText.trim() || (selectedText === nodeText && nodeText.trim())) {
464
+ if (!nodeText.trim() ||
465
+ (selectedText === nodeText && nodeText.trim())) {
447
466
  event.preventDefault();
448
- Transforms.setNodes(editor, { type: 'paragraph', listType: undefined, indent: undefined }, {
449
- match: n => !Editor.isEditor(n) && Element.isElement(n) && n.type === 'list-item',
450
- split: true
467
+ Transforms.setNodes(editor, { type: "paragraph", listType: undefined, indent: undefined }, {
468
+ match: (n) => !Editor.isEditor(n) &&
469
+ Element.isElement(n) &&
470
+ n.type === "list-item",
471
+ split: true,
451
472
  });
452
473
  }
453
474
  }
@@ -466,43 +487,45 @@ export const ReactSlate = forwardRef((props, ref) => {
466
487
  // Render each row
467
488
  return Object.entries(groupsByRow)
468
489
  .sort(([a], [b]) => parseInt(a) - parseInt(b))
469
- .map(([rowIndex, rowGroups]) => (_jsx("div", { className: "toolbar-row", children: rowGroups.map(group => renderToolbarGroup(group, parseInt(rowIndex))) }, `row-${rowIndex}`)));
470
- })() })), _jsx(Editable, { className: classNames(readOnly ? "bg-gray-4" : "bg-gray-5", "focus-shadow"), readOnly: readOnly, placeholder: placeholder, onFocus: onFocus, onBlur: onBlur, onKeyDown: handleKeyDown, renderElement: ({ attributes, children, element }) => {
490
+ .map(([rowIndex, rowGroups]) => (_jsx("div", { className: "toolbar-row", children: rowGroups.map((group) => renderToolbarGroup(group, parseInt(rowIndex))) }, `row-${rowIndex}`)));
491
+ })() })), _jsx(Editable, { className: classNames(readOnly ? "bg-gray-4" : "bg-gray-5", "focus-shadow p-2"), readOnly: readOnly, placeholder: placeholder, onFocus: onFocus, onBlur: onBlur, onKeyDown: handleKeyDown, renderElement: ({ attributes, children, element }) => {
471
492
  const style = {
472
- textAlign: element.align || 'left',
493
+ textAlign: element.align || "left",
473
494
  };
474
- if (element.type === 'link') {
475
- const isInternal = element.link?.type === 'internal';
476
- const url = isInternal ? '#' : (element.url || element.link?.url || '#');
477
- return (_jsx("a", { ...attributes, href: url, style: style, className: `slate-link ${isInternal ? 'internal-link' : 'external-link'}`, onClick: (e) => {
495
+ if (element.type === "link") {
496
+ const isInternal = element.link?.type === "internal";
497
+ const url = isInternal
498
+ ? "#"
499
+ : element.url || element.link?.url || "#";
500
+ return (_jsx("a", { ...attributes, href: url, style: style, className: `slate-link ${isInternal ? "internal-link" : "external-link"}`, onClick: (e) => {
478
501
  if (!readOnly) {
479
502
  e.preventDefault();
480
503
  editLink(element);
481
504
  }
482
505
  }, children: children }));
483
506
  }
484
- if (element.type === 'list-item') {
507
+ if (element.type === "list-item") {
485
508
  const indent = element.indent || 0;
486
- const listType = element.listType || 'unordered';
487
- const isOrdered = listType === 'ordered';
509
+ const listType = element.listType || "unordered";
510
+ const isOrdered = listType === "ordered";
488
511
  // Calculate proper numbering for ordered lists
489
512
  let listNumber = 1;
490
513
  if (isOrdered) {
491
514
  // Find the position of this item within its level
492
515
  const allElements = editor.children;
493
- const currentIndex = allElements.findIndex(el => el === element);
516
+ const currentIndex = allElements.findIndex((el) => el === element);
494
517
  // Count preceding list items at the same indent level and list type
495
518
  let count = 0;
496
519
  for (let i = 0; i < currentIndex; i++) {
497
520
  const prevElement = allElements[i];
498
521
  if (prevElement &&
499
- prevElement.type === 'list-item' &&
500
- prevElement.listType === 'ordered' &&
522
+ prevElement.type === "list-item" &&
523
+ prevElement.listType === "ordered" &&
501
524
  (prevElement.indent || 0) === indent) {
502
525
  count++;
503
526
  }
504
527
  else if (prevElement &&
505
- prevElement.type === 'list-item' &&
528
+ prevElement.type === "list-item" &&
506
529
  (prevElement.indent || 0) < indent) {
507
530
  // Reset count when we encounter a parent-level item
508
531
  count = 0;
@@ -512,17 +535,17 @@ export const ReactSlate = forwardRef((props, ref) => {
512
535
  }
513
536
  const listStyle = {
514
537
  ...style,
515
- position: 'relative',
516
- listStyleType: 'none',
538
+ position: "relative",
539
+ listStyleType: "none",
517
540
  };
518
- const bulletContent = isOrdered ? `${listNumber}.` : '';
541
+ const bulletContent = isOrdered ? `${listNumber}.` : "";
519
542
  return (_jsxs("div", { ...attributes, style: listStyle, className: `slate-list-item slate-list-${listType}`, "data-indent": indent, children: [_jsx("span", { className: "slate-list-bullet", children: bulletContent }), _jsx("div", { className: "slate-list-content", children: children })] }));
520
543
  }
521
544
  // Handle different block types using built-in SLATE_BLOCKS configuration
522
545
  const blockConfig = SLATE_BLOCKS[element.type];
523
- if (blockConfig && element.type === 'no-tag') {
546
+ if (blockConfig && element.type === "no-tag") {
524
547
  // Special handling for no-tag blocks (plain text without wrapper)
525
- return _jsx("span", { ...attributes, style: style, children: children });
548
+ return (_jsx("span", { ...attributes, style: style, children: children }));
526
549
  }
527
550
  // For standard blocks, use the appropriate HTML tag
528
551
  if (blockConfig) {
@@ -530,17 +553,17 @@ export const ReactSlate = forwardRef((props, ref) => {
530
553
  return React.createElement(tagName, { ...attributes, style }, children);
531
554
  }
532
555
  // Default fallback to paragraph
533
- return _jsx("p", { ...attributes, style: style, children: children });
556
+ return (_jsx("p", { ...attributes, style: style, children: children }));
534
557
  }, renderLeaf: ({ attributes, children, leaf }) => {
535
558
  let el = _jsx("span", { ...attributes, children: children });
536
559
  // Apply marks using the built-in SLATE_MARKS configuration
537
- simplifiedProfile.marks.forEach(markId => {
560
+ simplifiedProfile.marks.forEach((markId) => {
538
561
  if (leaf[markId]) {
539
562
  const markConfig = SLATE_MARKS[markId];
540
563
  if (markConfig) {
541
- if (markId === 'extrabold') {
564
+ if (markId === "extrabold") {
542
565
  // Special handling for extrabold with CSS class
543
- el = (_jsx("span", { className: "extrabold", children: el }));
566
+ el = _jsx("span", { className: "extrabold", children: el });
544
567
  }
545
568
  else {
546
569
  // Standard HTML tag rendering
@@ -557,6 +580,6 @@ export const ReactSlate = forwardRef((props, ref) => {
557
580
  setLinkDialogCallback(null);
558
581
  } }))] }));
559
582
  });
560
- ReactSlate.displayName = 'ReactSlate';
583
+ ReactSlate.displayName = "ReactSlate";
561
584
  export default ReactSlate;
562
585
  //# sourceMappingURL=ReactSlate.js.map