editium 1.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,3128 @@
1
+ import { jsxs, Fragment, jsx } from 'react/jsx-runtime';
2
+ import React, { useState, useRef, useEffect, useCallback, useMemo } from 'react';
3
+ import { Editor, Element, Transforms, Text, Range, createEditor } from 'slate';
4
+ import { ReactEditor, useSlate, useSlateStatic, useSelected, useFocused, withReact, Slate, Editable } from 'slate-react';
5
+ import { HistoryEditor, withHistory } from 'slate-history';
6
+ import { MagnifyingGlassIcon, ChevronLeftIcon, ChevronRightIcon, XMarkIcon, ArrowsPointingInIcon, ArrowsPointingOutIcon, ArrowTopRightOnSquareIcon, ArrowUturnLeftIcon, ArrowUturnRightIcon, LinkIcon, PhotoIcon, TableCellsIcon, CodeBracketIcon, ListBulletIcon, ArrowRightIcon, ArrowLeftIcon, ChevronDownIcon, PlusIcon, MinusIcon, Bars3BottomLeftIcon, Bars3Icon, Bars3BottomRightIcon, TrashIcon } from '@heroicons/react/24/outline';
7
+
8
+ /******************************************************************************
9
+ Copyright (c) Microsoft Corporation.
10
+
11
+ Permission to use, copy, modify, and/or distribute this software for any
12
+ purpose with or without fee is hereby granted.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
15
+ REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
16
+ AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
17
+ INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
18
+ LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
19
+ OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
20
+ PERFORMANCE OF THIS SOFTWARE.
21
+ ***************************************************************************** */
22
+ /* global Reflect, Promise, SuppressedError, Symbol, Iterator */
23
+
24
+
25
+ var __assign = function() {
26
+ __assign = Object.assign || function __assign(t) {
27
+ for (var s, i = 1, n = arguments.length; i < n; i++) {
28
+ s = arguments[i];
29
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p];
30
+ }
31
+ return t;
32
+ };
33
+ return __assign.apply(this, arguments);
34
+ };
35
+
36
+ function __awaiter(thisArg, _arguments, P, generator) {
37
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
38
+ return new (P || (P = Promise))(function (resolve, reject) {
39
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
40
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
41
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
42
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
43
+ });
44
+ }
45
+
46
+ function __generator(thisArg, body) {
47
+ var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g = Object.create((typeof Iterator === "function" ? Iterator : Object).prototype);
48
+ return g.next = verb(0), g["throw"] = verb(1), g["return"] = verb(2), typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g;
49
+ function verb(n) { return function (v) { return step([n, v]); }; }
50
+ function step(op) {
51
+ if (f) throw new TypeError("Generator is already executing.");
52
+ while (g && (g = 0, op[0] && (_ = 0)), _) try {
53
+ if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
54
+ if (y = 0, t) op = [op[0] & 2, t.value];
55
+ switch (op[0]) {
56
+ case 0: case 1: t = op; break;
57
+ case 4: _.label++; return { value: op[1], done: false };
58
+ case 5: _.label++; y = op[1]; op = [0]; continue;
59
+ case 7: op = _.ops.pop(); _.trys.pop(); continue;
60
+ default:
61
+ if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }
62
+ if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }
63
+ if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }
64
+ if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }
65
+ if (t[2]) _.ops.pop();
66
+ _.trys.pop(); continue;
67
+ }
68
+ op = body.call(thisArg, _);
69
+ } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }
70
+ if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };
71
+ }
72
+ }
73
+
74
+ function __spreadArray(to, from, pack) {
75
+ if (pack || arguments.length === 2) for (var i = 0, l = from.length, ar; i < l; i++) {
76
+ if (ar || !(i in from)) {
77
+ if (!ar) ar = Array.prototype.slice.call(from, 0, i);
78
+ ar[i] = from[i];
79
+ }
80
+ }
81
+ return to.concat(ar || Array.prototype.slice.call(from));
82
+ }
83
+
84
+ typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
85
+ var e = new Error(message);
86
+ return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
87
+ };
88
+
89
+ var isAlignmentActive = function (editor, alignment) {
90
+ var selection = editor.selection;
91
+ if (!selection)
92
+ return false;
93
+ var match = Array.from(Editor.nodes(editor, {
94
+ at: Editor.unhangRange(editor, selection),
95
+ match: function (n) {
96
+ return !Editor.isEditor(n) &&
97
+ Element.isElement(n) &&
98
+ n.align === alignment;
99
+ },
100
+ }))[0];
101
+ return !!match;
102
+ };
103
+ var toggleAlignment = function (editor, alignment) {
104
+ var isActive = isAlignmentActive(editor, alignment);
105
+ Transforms.setNodes(editor, { align: isActive ? undefined : alignment }, {
106
+ match: function (n) {
107
+ return !Editor.isEditor(n) &&
108
+ Element.isElement(n) &&
109
+ ['paragraph', 'heading-one', 'heading-two', 'heading-three', 'heading-four', 'heading-five', 'heading-six', 'heading-seven', 'heading-eight'].includes(n.type);
110
+ }
111
+ });
112
+ };
113
+ var indentListItem = function (editor) {
114
+ var selection = editor.selection;
115
+ if (!selection)
116
+ return;
117
+ var listItemMatch = Array.from(Editor.nodes(editor, {
118
+ match: function (n) {
119
+ return !Editor.isEditor(n) &&
120
+ Element.isElement(n) &&
121
+ n.type === 'list-item';
122
+ },
123
+ }))[0];
124
+ if (!listItemMatch)
125
+ return;
126
+ var listMatch = Array.from(Editor.nodes(editor, {
127
+ match: function (n) {
128
+ return !Editor.isEditor(n) &&
129
+ Element.isElement(n) &&
130
+ ['bulleted-list', 'numbered-list'].includes(n.type);
131
+ },
132
+ }))[0];
133
+ if (listMatch) {
134
+ var parentList = listMatch[0];
135
+ var listType = parentList.type;
136
+ Transforms.wrapNodes(editor, { type: listType, children: [] }, {
137
+ match: function (n) {
138
+ return !Editor.isEditor(n) &&
139
+ Element.isElement(n) &&
140
+ n.type === 'list-item';
141
+ },
142
+ });
143
+ }
144
+ };
145
+ var outdentListItem = function (editor) {
146
+ var selection = editor.selection;
147
+ if (!selection)
148
+ return;
149
+ var listNodes = Array.from(Editor.nodes(editor, {
150
+ match: function (n) {
151
+ return !Editor.isEditor(n) &&
152
+ Element.isElement(n) &&
153
+ ['bulleted-list', 'numbered-list'].includes(n.type);
154
+ },
155
+ }));
156
+ if (listNodes.length > 1) {
157
+ Transforms.unwrapNodes(editor, {
158
+ match: function (n) {
159
+ return !Editor.isEditor(n) &&
160
+ Element.isElement(n) &&
161
+ ['bulleted-list', 'numbered-list'].includes(n.type);
162
+ },
163
+ split: true,
164
+ });
165
+ }
166
+ else if (listNodes.length === 1) {
167
+ Transforms.unwrapNodes(editor, {
168
+ match: function (n) {
169
+ return !Editor.isEditor(n) &&
170
+ Element.isElement(n) &&
171
+ ['bulleted-list', 'numbered-list'].includes(n.type);
172
+ },
173
+ });
174
+ Transforms.setNodes(editor, { type: 'paragraph' }, {
175
+ match: function (n) {
176
+ return !Editor.isEditor(n) &&
177
+ Element.isElement(n) &&
178
+ n.type === 'list-item';
179
+ }
180
+ });
181
+ }
182
+ };
183
+ var isMarkActive = function (editor, format) {
184
+ var marks = Editor.marks(editor);
185
+ return marks ? marks[format] === true : false;
186
+ };
187
+ var isBlockActive = function (editor, format) {
188
+ var selection = editor.selection;
189
+ if (!selection)
190
+ return false;
191
+ var match = Array.from(Editor.nodes(editor, {
192
+ at: Editor.unhangRange(editor, selection),
193
+ match: function (n) {
194
+ return !Editor.isEditor(n) &&
195
+ Element.isElement(n) &&
196
+ n.type === format;
197
+ },
198
+ }))[0];
199
+ return !!match;
200
+ };
201
+ var toggleMark = function (editor, format) {
202
+ var isActive = isMarkActive(editor, format);
203
+ if (isActive) {
204
+ Editor.removeMark(editor, format);
205
+ }
206
+ else {
207
+ Editor.addMark(editor, format, true);
208
+ }
209
+ };
210
+ var applyColor = function (editor, color) {
211
+ if (color === null) {
212
+ Editor.removeMark(editor, 'color');
213
+ }
214
+ else {
215
+ Editor.addMark(editor, 'color', color);
216
+ }
217
+ };
218
+ var applyBackgroundColor = function (editor, color) {
219
+ if (color === null) {
220
+ Editor.removeMark(editor, 'backgroundColor');
221
+ }
222
+ else {
223
+ Editor.addMark(editor, 'backgroundColor', color);
224
+ }
225
+ };
226
+ var getActiveColor = function (editor) {
227
+ var marks = Editor.marks(editor);
228
+ return (marks === null || marks === void 0 ? void 0 : marks.color) ? String(marks.color) : null;
229
+ };
230
+ var getActiveBackgroundColor = function (editor) {
231
+ var marks = Editor.marks(editor);
232
+ return (marks === null || marks === void 0 ? void 0 : marks.backgroundColor) ? String(marks.backgroundColor) : null;
233
+ };
234
+ var toggleBlock = function (editor, format) {
235
+ var isActive = isBlockActive(editor, format);
236
+ var isList = ['bulleted-list', 'numbered-list'].includes(format);
237
+ Transforms.unwrapNodes(editor, {
238
+ match: function (n) {
239
+ return !Editor.isEditor(n) &&
240
+ Element.isElement(n) &&
241
+ ['bulleted-list', 'numbered-list'].includes(n.type);
242
+ },
243
+ split: true,
244
+ });
245
+ var newProperties;
246
+ if (format === 'list-item') {
247
+ newProperties = { type: isActive ? 'paragraph' : 'list-item' };
248
+ }
249
+ else {
250
+ newProperties = { type: isActive ? 'paragraph' : isList ? 'list-item' : format };
251
+ }
252
+ Transforms.setNodes(editor, newProperties);
253
+ if (!isActive && isList) {
254
+ var block = { type: format, children: [] };
255
+ Transforms.wrapNodes(editor, block);
256
+ }
257
+ };
258
+ var insertHorizontalRule = function (editor) {
259
+ var hr = {
260
+ type: 'horizontal-rule',
261
+ children: [{ text: '' }],
262
+ };
263
+ Transforms.insertNodes(editor, hr);
264
+ var paragraph = {
265
+ type: 'paragraph',
266
+ children: [{ text: '' }],
267
+ };
268
+ Transforms.insertNodes(editor, paragraph);
269
+ };
270
+ var insertImage = function (editor, url, alt, width) {
271
+ var image = {
272
+ type: 'image',
273
+ url: url,
274
+ alt: alt || 'Image',
275
+ width: width,
276
+ children: [{ text: '' }],
277
+ };
278
+ Transforms.insertNodes(editor, image);
279
+ var paragraph = {
280
+ type: 'paragraph',
281
+ children: [{ text: '' }],
282
+ };
283
+ Transforms.insertNodes(editor, paragraph);
284
+ };
285
+ var isValidImageUrl = function (url) {
286
+ try {
287
+ var parsedUrl = new URL(url);
288
+ var imageExtensions = ['.jpg', '.jpeg', '.png', '.gif', '.svg', '.webp', '.bmp', '.ico'];
289
+ var pathname_1 = parsedUrl.pathname.toLowerCase();
290
+ return imageExtensions.some(function (ext) { return pathname_1.endsWith(ext); }) ||
291
+ parsedUrl.protocol === 'data:' ||
292
+ pathname_1.includes('/image') ||
293
+ parsedUrl.hostname.includes('cdn') ||
294
+ parsedUrl.hostname.includes('imgur') ||
295
+ parsedUrl.hostname.includes('unsplash');
296
+ }
297
+ catch (_a) {
298
+ return false;
299
+ }
300
+ };
301
+ var insertLink = function (editor, url, title, target) {
302
+ if (editor.selection) {
303
+ wrapLink(editor, url, title, target);
304
+ }
305
+ };
306
+ var isLinkActive = function (editor) {
307
+ var link = Array.from(Editor.nodes(editor, {
308
+ match: function (n) {
309
+ return !Editor.isEditor(n) &&
310
+ Element.isElement(n) &&
311
+ n.type === 'link';
312
+ },
313
+ }))[0];
314
+ return !!link;
315
+ };
316
+ var unwrapLink = function (editor) {
317
+ Transforms.unwrapNodes(editor, {
318
+ match: function (n) {
319
+ return !Editor.isEditor(n) &&
320
+ Element.isElement(n) &&
321
+ n.type === 'link';
322
+ },
323
+ });
324
+ };
325
+ var wrapLink = function (editor, url, title, target) {
326
+ if (isLinkActive(editor)) {
327
+ unwrapLink(editor);
328
+ }
329
+ var selection = editor.selection;
330
+ var isCollapsed = selection && Range.isCollapsed(selection);
331
+ var link = __assign(__assign(__assign({ type: 'link', url: url }, (title && { title: title })), (target && { target: target })), { children: isCollapsed ? [{ text: url }] : [] });
332
+ if (isCollapsed) {
333
+ Transforms.insertNodes(editor, link);
334
+ }
335
+ else {
336
+ Transforms.wrapNodes(editor, link, { split: true });
337
+ Transforms.collapse(editor, { edge: 'end' });
338
+ }
339
+ };
340
+ var insertTable = function (editor, rows, cols) {
341
+ if (rows === void 0) { rows = 3; }
342
+ if (cols === void 0) { cols = 3; }
343
+ var tableRows = [];
344
+ for (var i = 0; i < rows; i++) {
345
+ var cells = [];
346
+ for (var j = 0; j < cols; j++) {
347
+ cells.push({
348
+ type: 'table-cell',
349
+ children: [{ text: '' }],
350
+ });
351
+ }
352
+ tableRows.push({
353
+ type: 'table-row',
354
+ children: cells,
355
+ });
356
+ }
357
+ var table = {
358
+ type: 'table',
359
+ children: tableRows,
360
+ };
361
+ var paragraph = {
362
+ type: 'paragraph',
363
+ children: [{ text: '' }],
364
+ };
365
+ Transforms.insertNodes(editor, [table, paragraph]);
366
+ };
367
+ var isInTable = function (editor) {
368
+ var selection = editor.selection;
369
+ if (!selection)
370
+ return false;
371
+ var tableMatch = Array.from(Editor.nodes(editor, {
372
+ at: selection,
373
+ match: function (n) {
374
+ return !Editor.isEditor(n) &&
375
+ Element.isElement(n) &&
376
+ n.type === 'table';
377
+ },
378
+ }))[0];
379
+ return !!tableMatch;
380
+ };
381
+ var addTableRow = function (editor) {
382
+ var _a;
383
+ var selection = editor.selection;
384
+ if (!selection)
385
+ return;
386
+ var tableMatch = Array.from(Editor.nodes(editor, {
387
+ at: selection,
388
+ match: function (n) {
389
+ return !Editor.isEditor(n) &&
390
+ Element.isElement(n) &&
391
+ n.type === 'table';
392
+ },
393
+ }))[0];
394
+ if (!tableMatch)
395
+ return;
396
+ var _b = tableMatch, table = _b[0], tablePath = _b[1];
397
+ var firstRow = table.children[0];
398
+ var colCount = ((_a = firstRow === null || firstRow === void 0 ? void 0 : firstRow.children) === null || _a === void 0 ? void 0 : _a.length) || 1;
399
+ var cells = [];
400
+ for (var i = 0; i < colCount; i++) {
401
+ cells.push({
402
+ type: 'table-cell',
403
+ children: [{ text: '' }],
404
+ });
405
+ }
406
+ var newRow = {
407
+ type: 'table-row',
408
+ children: cells,
409
+ };
410
+ Transforms.insertNodes(editor, newRow, {
411
+ at: __spreadArray(__spreadArray([], tablePath, true), [table.children.length], false),
412
+ });
413
+ };
414
+ var removeTableRow = function (editor) {
415
+ var selection = editor.selection;
416
+ if (!selection)
417
+ return;
418
+ var rowMatch = Array.from(Editor.nodes(editor, {
419
+ at: selection,
420
+ match: function (n) {
421
+ return !Editor.isEditor(n) &&
422
+ Element.isElement(n) &&
423
+ n.type === 'table-row';
424
+ },
425
+ }))[0];
426
+ if (!rowMatch)
427
+ return;
428
+ var _a = rowMatch, rowPath = _a[1];
429
+ var tableMatch = Array.from(Editor.nodes(editor, {
430
+ at: selection,
431
+ match: function (n) {
432
+ return !Editor.isEditor(n) &&
433
+ Element.isElement(n) &&
434
+ n.type === 'table';
435
+ },
436
+ }))[0];
437
+ if (tableMatch) {
438
+ var table = tableMatch[0];
439
+ if (table.children.length <= 1) {
440
+ Transforms.removeNodes(editor, {
441
+ match: function (n) {
442
+ return !Editor.isEditor(n) &&
443
+ Element.isElement(n) &&
444
+ n.type === 'table';
445
+ },
446
+ });
447
+ return;
448
+ }
449
+ }
450
+ Transforms.removeNodes(editor, { at: rowPath });
451
+ };
452
+ var addTableColumn = function (editor) {
453
+ var selection = editor.selection;
454
+ if (!selection)
455
+ return;
456
+ var tableMatch = Array.from(Editor.nodes(editor, {
457
+ at: selection,
458
+ match: function (n) {
459
+ return !Editor.isEditor(n) &&
460
+ Element.isElement(n) &&
461
+ n.type === 'table';
462
+ },
463
+ }))[0];
464
+ if (!tableMatch)
465
+ return;
466
+ var _a = tableMatch, table = _a[0], tablePath = _a[1];
467
+ table.children.forEach(function (_row, rowIndex) {
468
+ var newCell = {
469
+ type: 'table-cell',
470
+ children: [{ text: '' }],
471
+ };
472
+ Transforms.insertNodes(editor, newCell, {
473
+ at: __spreadArray(__spreadArray([], tablePath, true), [rowIndex, table.children[rowIndex].children.length], false),
474
+ });
475
+ });
476
+ };
477
+ var removeTableColumn = function (editor) {
478
+ var _a, _b;
479
+ var selection = editor.selection;
480
+ if (!selection)
481
+ return;
482
+ var cellMatch = Array.from(Editor.nodes(editor, {
483
+ at: selection,
484
+ match: function (n) {
485
+ return !Editor.isEditor(n) &&
486
+ Element.isElement(n) &&
487
+ n.type === 'table-cell';
488
+ },
489
+ }))[0];
490
+ if (!cellMatch)
491
+ return;
492
+ var _c = cellMatch, cellPath = _c[1];
493
+ var cellIndex = cellPath[cellPath.length - 1];
494
+ var tableMatch = Array.from(Editor.nodes(editor, {
495
+ at: selection,
496
+ match: function (n) {
497
+ return !Editor.isEditor(n) &&
498
+ Element.isElement(n) &&
499
+ n.type === 'table';
500
+ },
501
+ }))[0];
502
+ if (!tableMatch)
503
+ return;
504
+ var _d = tableMatch, table = _d[0], tablePath = _d[1];
505
+ if (((_b = (_a = table.children[0]) === null || _a === void 0 ? void 0 : _a.children) === null || _b === void 0 ? void 0 : _b.length) <= 1) {
506
+ Transforms.removeNodes(editor, { at: tablePath });
507
+ return;
508
+ }
509
+ for (var rowIndex = table.children.length - 1; rowIndex >= 0; rowIndex--) {
510
+ Transforms.removeNodes(editor, {
511
+ at: __spreadArray(__spreadArray([], tablePath, true), [rowIndex, cellIndex], false),
512
+ });
513
+ }
514
+ };
515
+ var setTableAlignment = function (editor, alignment) {
516
+ var selection = editor.selection;
517
+ if (!selection)
518
+ return;
519
+ var tableMatch = Array.from(Editor.nodes(editor, {
520
+ at: selection,
521
+ match: function (n) {
522
+ return !Editor.isEditor(n) &&
523
+ Element.isElement(n) &&
524
+ n.type === 'table';
525
+ },
526
+ }))[0];
527
+ if (!tableMatch)
528
+ return;
529
+ var _a = tableMatch, tablePath = _a[1];
530
+ Transforms.setNodes(editor, { align: alignment }, { at: tablePath });
531
+ };
532
+ var findAllMatches = function (editor, searchQuery) {
533
+ if (!searchQuery)
534
+ return [];
535
+ var matches = [];
536
+ var searchLower = searchQuery.toLowerCase();
537
+ var textNodes = Array.from(Editor.nodes(editor, {
538
+ at: [],
539
+ match: function (n) { return Text.isText(n); },
540
+ }));
541
+ textNodes.forEach(function (_a) {
542
+ var node = _a[0], path = _a[1];
543
+ var textNode = node;
544
+ var text = textNode.text;
545
+ var textLower = text.toLowerCase();
546
+ var index = 0;
547
+ while ((index = textLower.indexOf(searchLower, index)) !== -1) {
548
+ matches.push({
549
+ path: path,
550
+ offset: index,
551
+ text: text.substring(index, index + searchQuery.length),
552
+ });
553
+ index += searchQuery.length;
554
+ }
555
+ });
556
+ return matches;
557
+ };
558
+ var navigateToMatch = function (editor, match) {
559
+ var _a;
560
+ var start = { path: match.path, offset: match.offset };
561
+ var end = { path: match.path, offset: match.offset + match.text.length };
562
+ Transforms.select(editor, { anchor: start, focus: end });
563
+ var domRange = ReactEditor.toDOMRange(editor, editor.selection);
564
+ (_a = domRange.startContainer.parentElement) === null || _a === void 0 ? void 0 : _a.scrollIntoView({
565
+ behavior: 'smooth',
566
+ block: 'center',
567
+ });
568
+ };
569
+ var replaceMatch = function (editor, match, replaceText) {
570
+ var start = { path: match.path, offset: match.offset };
571
+ var end = { path: match.path, offset: match.offset + match.text.length };
572
+ Transforms.select(editor, { anchor: start, focus: end });
573
+ Transforms.insertText(editor, replaceText);
574
+ };
575
+ var replaceAllMatches = function (editor, matches, replaceText) {
576
+ var sortedMatches = __spreadArray([], matches, true).reverse();
577
+ Editor.withoutNormalizing(editor, function () {
578
+ sortedMatches.forEach(function (match) {
579
+ var start = { path: match.path, offset: match.offset };
580
+ var end = { path: match.path, offset: match.offset + match.text.length };
581
+ Transforms.select(editor, { anchor: start, focus: end });
582
+ Transforms.delete(editor);
583
+ Transforms.insertText(editor, replaceText, { at: start });
584
+ });
585
+ });
586
+ };
587
+ var serializeToHtml = function (nodes) {
588
+ return nodes.map(function (node) { return serializeNode(node); }).join('');
589
+ };
590
+ var serializeNode = function (node) {
591
+ if (Text.isText(node)) {
592
+ var textNode = node;
593
+ var string = escapeHtml(textNode.text);
594
+ var styles = [];
595
+ if (textNode.color)
596
+ styles.push("color: ".concat(textNode.color));
597
+ if (textNode.backgroundColor)
598
+ styles.push("background-color: ".concat(textNode.backgroundColor));
599
+ var styleAttr = styles.length > 0 ? " style=\"".concat(styles.join('; '), "\"") : '';
600
+ if (textNode.bold)
601
+ string = "<strong>".concat(string, "</strong>");
602
+ if (textNode.italic)
603
+ string = "<em>".concat(string, "</em>");
604
+ if (textNode.underline)
605
+ string = "<u>".concat(string, "</u>");
606
+ if (textNode.code)
607
+ string = "<code>".concat(string, "</code>");
608
+ if (textNode.strikethrough)
609
+ string = "<s>".concat(string, "</s>");
610
+ if (textNode.superscript)
611
+ string = "<sup>".concat(string, "</sup>");
612
+ if (textNode.subscript)
613
+ string = "<sub>".concat(string, "</sub>");
614
+ if (styleAttr) {
615
+ string = "<span".concat(styleAttr, ">").concat(string, "</span>");
616
+ }
617
+ return string;
618
+ }
619
+ var elementNode = node;
620
+ var children = elementNode.children.map(function (n) { return serializeNode(n); }).join('');
621
+ var alignStyle = elementNode.align ? " style=\"text-align: ".concat(elementNode.align, "\"") : '';
622
+ switch (elementNode.type) {
623
+ case 'paragraph':
624
+ return "<p".concat(alignStyle, ">").concat(children, "</p>");
625
+ case 'heading-one':
626
+ return "<h1".concat(alignStyle, ">").concat(children, "</h1>");
627
+ case 'heading-two':
628
+ return "<h2".concat(alignStyle, ">").concat(children, "</h2>");
629
+ case 'heading-three':
630
+ return "<h3".concat(alignStyle, ">").concat(children, "</h3>");
631
+ case 'heading-four':
632
+ return "<h4".concat(alignStyle, ">").concat(children, "</h4>");
633
+ case 'heading-five':
634
+ return "<h5".concat(alignStyle, ">").concat(children, "</h5>");
635
+ case 'heading-six':
636
+ return "<h6".concat(alignStyle, ">").concat(children, "</h6>");
637
+ case 'heading-seven':
638
+ return "<h7".concat(alignStyle, ">").concat(children, "</h7>");
639
+ case 'heading-eight':
640
+ return "<h8".concat(alignStyle, ">").concat(children, "</h8>");
641
+ case 'bulleted-list':
642
+ return "<ul>".concat(children, "</ul>");
643
+ case 'numbered-list':
644
+ return "<ol>".concat(children, "</ol>");
645
+ case 'list-item':
646
+ return "<li>".concat(children, "</li>");
647
+ case 'blockquote':
648
+ return "<blockquote".concat(alignStyle, ">").concat(children, "</blockquote>");
649
+ case 'code-block':
650
+ return "<pre><code>".concat(children, "</code></pre>");
651
+ case 'horizontal-rule':
652
+ return "<hr />";
653
+ case 'table':
654
+ var tableNode = elementNode;
655
+ var tableAlignStyle = tableNode.align ? " margin-left: ".concat(tableNode.align === 'center' ? 'auto' :
656
+ tableNode.align === 'right' ? 'auto' : '0', "; margin-right: ").concat(tableNode.align === 'center' ? 'auto' :
657
+ tableNode.align === 'right' ? '0' : 'auto', ";") : '';
658
+ var tableWidthStyle = tableNode.width ? " width: ".concat(tableNode.width, "px; max-width: 100%;") : ' width: 100%;';
659
+ return "<table style=\"border-collapse: collapse;".concat(tableWidthStyle, " margin-top: 16px; margin-bottom: 16px;").concat(tableAlignStyle, "\">").concat(children, "</table>");
660
+ case 'table-row':
661
+ return "<tr>".concat(children, "</tr>");
662
+ case 'table-cell':
663
+ var cellNode = elementNode;
664
+ var cellAlignStyle = cellNode.align ? " text-align: ".concat(cellNode.align, ";") : '';
665
+ return "<td style=\"border: 1px solid #ddd; padding: 8px;".concat(cellAlignStyle, "\">").concat(children, "</td>");
666
+ case 'image':
667
+ var imageNode = elementNode;
668
+ var altAttr = imageNode.alt ? " alt=\"".concat(escapeHtml(imageNode.alt), "\"") : ' alt="Image"';
669
+ var widthAttr = imageNode.width ? " width=\"".concat(imageNode.width, "\"") : '';
670
+ var heightAttr = imageNode.height ? " height=\"".concat(imageNode.height, "\"") : '';
671
+ var imgAlignStyle = imageNode.align ? " style=\"display: block; margin: ".concat(imageNode.align === 'center' ? '0 auto' :
672
+ imageNode.align === 'right' ? '0 0 0 auto' : '0', ";\"") : '';
673
+ return "<img src=\"".concat(escapeHtml(imageNode.url), "\"").concat(altAttr).concat(widthAttr).concat(heightAttr).concat(imgAlignStyle, " />");
674
+ case 'link':
675
+ var linkNode = elementNode;
676
+ var titleAttr = linkNode.title ? " title=\"".concat(escapeHtml(linkNode.title), "\"") : '';
677
+ var targetAttr = linkNode.target ? " target=\"".concat(linkNode.target, "\"") : '';
678
+ var relAttr = linkNode.target === '_blank' ? ' rel="noopener noreferrer"' : '';
679
+ return "<a href=\"".concat(escapeHtml(linkNode.url), "\"").concat(titleAttr).concat(targetAttr).concat(relAttr, ">").concat(children, "</a>");
680
+ default:
681
+ return children;
682
+ }
683
+ };
684
+ var escapeHtml = function (text) {
685
+ var div = document.createElement('div');
686
+ div.textContent = text;
687
+ return div.innerHTML;
688
+ };
689
+ var defaultInitialValue = [
690
+ {
691
+ type: 'paragraph',
692
+ children: [{ text: '' }],
693
+ },
694
+ ];
695
+ var getTextContent = function (nodes) {
696
+ return nodes
697
+ .map(function (node) {
698
+ if (node.text !== undefined) {
699
+ return node.text;
700
+ }
701
+ if (node.children) {
702
+ return getTextContent(node.children);
703
+ }
704
+ return '';
705
+ })
706
+ .join('');
707
+ };
708
+ var countWords = function (text) {
709
+ var trimmed = text.trim();
710
+ if (trimmed === '')
711
+ return 0;
712
+ return trimmed.split(/\s+/).filter(function (word) { return word.length > 0; }).length;
713
+ };
714
+ var countCharacters = function (text) {
715
+ return text.length;
716
+ };
717
+ var countCharactersNoSpaces = function (text) {
718
+ return text.replace(/\s/g, '').length;
719
+ };
720
+
721
+ var Dropdown = function (_a) {
722
+ var trigger = _a.trigger, children = _a.children, title = _a.title;
723
+ var _b = useState(false), isOpen = _b[0], setIsOpen = _b[1];
724
+ var dropdownRef = useRef(null);
725
+ useEffect(function () {
726
+ var handleClickOutside = function (event) {
727
+ if (dropdownRef.current && !dropdownRef.current.contains(event.target)) {
728
+ setIsOpen(false);
729
+ }
730
+ };
731
+ document.addEventListener('mousedown', handleClickOutside);
732
+ return function () { return document.removeEventListener('mousedown', handleClickOutside); };
733
+ }, []);
734
+ return (jsxs("div", { ref: dropdownRef, style: { position: 'relative', display: 'inline-block' }, children: [jsxs("button", { title: title, onMouseDown: function (e) {
735
+ e.preventDefault();
736
+ setIsOpen(!isOpen);
737
+ }, style: {
738
+ backgroundColor: isOpen ? '#dee2e6' : 'transparent',
739
+ border: 'none',
740
+ borderRadius: '3px',
741
+ padding: '5px 8px',
742
+ margin: '0',
743
+ cursor: 'pointer',
744
+ fontSize: '14px',
745
+ fontWeight: '400',
746
+ color: '#222f3e',
747
+ transition: 'background-color 0.1s ease',
748
+ display: 'inline-flex',
749
+ alignItems: 'center',
750
+ justifyContent: 'center',
751
+ minHeight: '28px',
752
+ boxShadow: 'none',
753
+ whiteSpace: 'nowrap',
754
+ }, onMouseEnter: function (e) {
755
+ if (!isOpen) {
756
+ e.currentTarget.style.backgroundColor = '#e9ecef';
757
+ }
758
+ }, onMouseLeave: function (e) {
759
+ if (!isOpen) {
760
+ e.currentTarget.style.backgroundColor = 'transparent';
761
+ }
762
+ }, children: [trigger, jsx(ChevronDownIcon, { style: { marginLeft: '4px', width: '12px', height: '12px' } })] }), isOpen && (jsx("div", { style: {
763
+ position: 'absolute',
764
+ top: '100%',
765
+ left: '0',
766
+ zIndex: 9999,
767
+ backgroundColor: '#ffffff',
768
+ border: '1px solid #ccc',
769
+ borderRadius: '3px',
770
+ boxShadow: '0 2px 8px rgba(0, 0, 0, 0.15)',
771
+ minWidth: '180px',
772
+ marginTop: '4px',
773
+ overflow: 'hidden',
774
+ padding: '4px 0'
775
+ }, children: children }))] }));
776
+ };
777
+ var ToolbarButton = function (_a) {
778
+ var active = _a.active, onMouseDown = _a.onMouseDown, children = _a.children, title = _a.title;
779
+ return (jsx("button", { title: title, onMouseDown: onMouseDown, style: {
780
+ backgroundColor: active ? '#dee2e6' : 'transparent',
781
+ border: 'none',
782
+ borderRadius: '3px',
783
+ padding: '5px 8px',
784
+ margin: '0',
785
+ cursor: 'pointer',
786
+ fontSize: '14px',
787
+ fontWeight: '400',
788
+ color: '#222f3e',
789
+ transition: 'background-color 0.1s ease',
790
+ display: 'inline-flex',
791
+ alignItems: 'center',
792
+ justifyContent: 'center',
793
+ minHeight: '28px',
794
+ boxShadow: 'none',
795
+ whiteSpace: 'nowrap',
796
+ }, onMouseEnter: function (e) {
797
+ if (!active) {
798
+ e.currentTarget.style.backgroundColor = '#e9ecef';
799
+ }
800
+ }, onMouseLeave: function (e) {
801
+ if (!active) {
802
+ e.currentTarget.style.backgroundColor = 'transparent';
803
+ }
804
+ }, children: children }));
805
+ };
806
+ var DropdownItem = function (_a) {
807
+ var active = _a.active, onMouseDown = _a.onMouseDown, children = _a.children, icon = _a.icon;
808
+ return (jsxs("button", { onMouseDown: onMouseDown, style: {
809
+ width: '100%',
810
+ padding: '6px 16px',
811
+ border: 'none',
812
+ backgroundColor: active ? '#e7f4ff' : 'transparent',
813
+ color: '#222f3e',
814
+ fontSize: '14px',
815
+ fontWeight: '400',
816
+ cursor: 'pointer',
817
+ textAlign: 'left',
818
+ transition: 'background-color 0.1s ease',
819
+ borderRadius: '0',
820
+ display: 'flex',
821
+ alignItems: 'center',
822
+ gap: '10px',
823
+ }, onMouseEnter: function (e) {
824
+ e.currentTarget.style.backgroundColor = '#e7f4ff';
825
+ }, onMouseLeave: function (e) {
826
+ if (!active) {
827
+ e.currentTarget.style.backgroundColor = 'transparent';
828
+ }
829
+ }, children: [icon && jsx("span", { style: { width: '16px', height: '16px', display: 'flex', alignItems: 'center', justifyContent: 'center' }, children: icon }), children] }));
830
+ };
831
+ var ToolbarSeparator = function () { return (jsx("div", { style: {
832
+ width: '1px',
833
+ height: '24px',
834
+ backgroundColor: '#ccc',
835
+ margin: '0 4px',
836
+ alignSelf: 'center',
837
+ } })); };
838
+ var Toolbar = function (_a) {
839
+ var _b;
840
+ var items = _a.items, className = _a.className, onViewOutput = _a.onViewOutput; _a.onEditLink; var _c = _a.searchQuery, propSearchQuery = _c === void 0 ? '' : _c, _d = _a.searchMatches, propSearchMatches = _d === void 0 ? [] : _d, _e = _a.currentMatchIndex, propCurrentMatchIndex = _e === void 0 ? 0 : _e, onSearchQueryChange = _a.onSearchQueryChange, onSearchMatchesChange = _a.onSearchMatchesChange, onCurrentMatchIndexChange = _a.onCurrentMatchIndexChange, _f = _a.isFullscreen, isFullscreen = _f === void 0 ? false : _f, onFullscreenToggle = _a.onFullscreenToggle;
841
+ var editor = useSlate();
842
+ var _g = useState(false), showLinkModal = _g[0], setShowLinkModal = _g[1];
843
+ var _h = useState(''), linkText = _h[0], setLinkText = _h[1];
844
+ var _j = useState(''), linkUrl = _j[0], setLinkUrl = _j[1];
845
+ var _k = useState(''), linkTitle = _k[0], setLinkTitle = _k[1];
846
+ var _l = useState('_self'), linkTarget = _l[0], setLinkTarget = _l[1];
847
+ var _m = useState(false), isEditingLink = _m[0], setIsEditingLink = _m[1];
848
+ var _o = useState(false); _o[0]; _o[1];
849
+ var _p = useState({ x: 0, y: 0 }); _p[0]; _p[1];
850
+ var _q = useState(false), showImageModal = _q[0], setShowImageModal = _q[1];
851
+ var _r = useState(''), imageUrl = _r[0], setImageUrl = _r[1];
852
+ var _s = useState(''), imageAlt = _s[0], setImageAlt = _s[1];
853
+ var _t = useState(null), imageFile = _t[0], setImageFile = _t[1];
854
+ var _u = useState(''), imageUploadError = _u[0], setImageUploadError = _u[1];
855
+ var _v = useState(false), isReplacingImage = _v[0], setIsReplacingImage = _v[1];
856
+ var _w = useState(null), replacingImagePath = _w[0], setReplacingImagePath = _w[1];
857
+ var _x = useState(false), showTableModal = _x[0], setShowTableModal = _x[1];
858
+ var _y = useState(3), tableRows = _y[0], setTableRows = _y[1];
859
+ var _z = useState(3), tableCols = _z[0], setTableCols = _z[1];
860
+ var _0 = useState(false), showFindReplace = _0[0], setShowFindReplace = _0[1];
861
+ var _1 = useState(''), replaceText = _1[0], setReplaceText = _1[1];
862
+ var _2 = useState(0), totalMatches = _2[0], setTotalMatches = _2[1];
863
+ var searchQuery = propSearchQuery;
864
+ var searchMatches = propSearchMatches;
865
+ var currentMatchIndex = propCurrentMatchIndex;
866
+ var handleMarkToggle = function (event, format) {
867
+ event.preventDefault();
868
+ toggleMark(editor, format);
869
+ };
870
+ var handleBlockToggle = function (event, format) {
871
+ event.preventDefault();
872
+ toggleBlock(editor, format);
873
+ };
874
+ var handleAlignmentToggle = function (event, alignment) {
875
+ event.preventDefault();
876
+ toggleAlignment(editor, alignment);
877
+ };
878
+ var handleIndent = function (event) {
879
+ event.preventDefault();
880
+ indentListItem(editor);
881
+ };
882
+ var handleOutdent = function (event) {
883
+ event.preventDefault();
884
+ outdentListItem(editor);
885
+ };
886
+ var handleUndo = function (event) {
887
+ event.preventDefault();
888
+ HistoryEditor.undo(editor);
889
+ };
890
+ var handleRedo = function (event) {
891
+ event.preventDefault();
892
+ HistoryEditor.redo(editor);
893
+ };
894
+ var handleLinkToggle = function (event) {
895
+ event.preventDefault();
896
+ var selection = editor.selection;
897
+ if (selection) {
898
+ var selectedText = Editor.string(editor, selection);
899
+ setLinkText(selectedText);
900
+ }
901
+ else {
902
+ setLinkText('');
903
+ }
904
+ setLinkUrl('');
905
+ setLinkTitle('');
906
+ setLinkTarget('_self');
907
+ setIsEditingLink(false);
908
+ setShowLinkModal(true);
909
+ };
910
+ var handleInsertLink = function () {
911
+ if (!linkUrl.trim()) {
912
+ alert('URL is required');
913
+ return;
914
+ }
915
+ try {
916
+ new URL(linkUrl);
917
+ }
918
+ catch (_a) {
919
+ alert('Please enter a valid URL (e.g., https://example.com)');
920
+ return;
921
+ }
922
+ if (isEditingLink) {
923
+ Transforms.setNodes(editor, {
924
+ url: linkUrl,
925
+ title: linkTitle || undefined,
926
+ target: linkTarget
927
+ }, {
928
+ match: function (n) { return n.type === 'link'; }
929
+ });
930
+ if (linkText.trim() && editor.selection) {
931
+ Transforms.delete(editor, { at: editor.selection });
932
+ Transforms.insertText(editor, linkText, { at: editor.selection });
933
+ }
934
+ }
935
+ else {
936
+ if (linkText.trim()) {
937
+ if (editor.selection) {
938
+ Transforms.delete(editor);
939
+ }
940
+ Transforms.insertNodes(editor, {
941
+ type: 'link',
942
+ url: linkUrl,
943
+ title: linkTitle || undefined,
944
+ target: linkTarget,
945
+ children: [{ text: linkText }],
946
+ });
947
+ Transforms.move(editor);
948
+ }
949
+ else if (editor.selection && !Range.isCollapsed(editor.selection)) {
950
+ insertLink(editor, linkUrl, linkTitle || undefined, linkTarget);
951
+ }
952
+ else {
953
+ Transforms.insertNodes(editor, {
954
+ type: 'link',
955
+ url: linkUrl,
956
+ title: linkTitle || undefined,
957
+ target: linkTarget,
958
+ children: [{ text: linkUrl }],
959
+ });
960
+ Transforms.move(editor);
961
+ }
962
+ }
963
+ setShowLinkModal(false);
964
+ setLinkText('');
965
+ setLinkUrl('');
966
+ setLinkTitle('');
967
+ setLinkTarget('_self');
968
+ setIsEditingLink(false);
969
+ };
970
+ var handleImageToggle = function (event) {
971
+ event.preventDefault();
972
+ setImageUrl('');
973
+ setImageAlt('');
974
+ setImageFile(null);
975
+ setImageUploadError('');
976
+ setIsReplacingImage(false);
977
+ setReplacingImagePath(null);
978
+ setShowImageModal(true);
979
+ };
980
+ var handleInsertImage = function () { return __awaiter(void 0, void 0, void 0, function () {
981
+ var editiumProps, uploadedUrl, error_1;
982
+ return __generator(this, function (_a) {
983
+ switch (_a.label) {
984
+ case 0:
985
+ setImageUploadError('');
986
+ if (!imageFile) return [3 /*break*/, 5];
987
+ editiumProps = window.__editiumProps;
988
+ if (!(editiumProps === null || editiumProps === void 0 ? void 0 : editiumProps.onImageUpload)) {
989
+ setImageUploadError('Upload not configured. Please define onImageUpload in your app.');
990
+ return [2 /*return*/];
991
+ }
992
+ _a.label = 1;
993
+ case 1:
994
+ _a.trys.push([1, 3, , 4]);
995
+ return [4 /*yield*/, editiumProps.onImageUpload(imageFile)];
996
+ case 2:
997
+ uploadedUrl = _a.sent();
998
+ if (isReplacingImage && replacingImagePath) {
999
+ Transforms.setNodes(editor, {
1000
+ url: uploadedUrl,
1001
+ alt: imageAlt || imageFile.name
1002
+ }, { at: replacingImagePath });
1003
+ }
1004
+ else {
1005
+ insertImage(editor, uploadedUrl, imageAlt || imageFile.name);
1006
+ }
1007
+ setShowImageModal(false);
1008
+ setImageUrl('');
1009
+ setImageAlt('');
1010
+ setImageFile(null);
1011
+ setIsReplacingImage(false);
1012
+ setReplacingImagePath(null);
1013
+ return [3 /*break*/, 4];
1014
+ case 3:
1015
+ error_1 = _a.sent();
1016
+ setImageUploadError('Failed to upload image: ' + error_1.message);
1017
+ return [3 /*break*/, 4];
1018
+ case 4: return [2 /*return*/];
1019
+ case 5:
1020
+ if (!imageUrl.trim()) {
1021
+ setImageUploadError('Please enter an image URL or select a file');
1022
+ return [2 /*return*/];
1023
+ }
1024
+ if (!isValidImageUrl(imageUrl)) {
1025
+ setImageUploadError('Please enter a valid image URL');
1026
+ return [2 /*return*/];
1027
+ }
1028
+ if (isReplacingImage && replacingImagePath) {
1029
+ Transforms.setNodes(editor, {
1030
+ url: imageUrl,
1031
+ alt: imageAlt || 'Image'
1032
+ }, { at: replacingImagePath });
1033
+ }
1034
+ else {
1035
+ insertImage(editor, imageUrl, imageAlt || 'Image');
1036
+ }
1037
+ setShowImageModal(false);
1038
+ setImageUrl('');
1039
+ setImageAlt('');
1040
+ setImageFile(null);
1041
+ setIsReplacingImage(false);
1042
+ setReplacingImagePath(null);
1043
+ return [2 /*return*/];
1044
+ }
1045
+ });
1046
+ }); };
1047
+ var handleFileChange = function (e) {
1048
+ var _a;
1049
+ var file = (_a = e.target.files) === null || _a === void 0 ? void 0 : _a[0];
1050
+ if (file) {
1051
+ if (!file.type.startsWith('image/')) {
1052
+ setImageUploadError('Please select an image file');
1053
+ return;
1054
+ }
1055
+ if (file.size > 5 * 1024 * 1024) {
1056
+ setImageUploadError('Image size should be less than 5MB');
1057
+ return;
1058
+ }
1059
+ setImageFile(file);
1060
+ setImageUploadError('');
1061
+ }
1062
+ };
1063
+ var handleTableToggle = function (event) {
1064
+ event.preventDefault();
1065
+ setShowTableModal(true);
1066
+ setTableRows(3);
1067
+ setTableCols(3);
1068
+ };
1069
+ var handleInsertTable = function () {
1070
+ insertTable(editor, tableRows, tableCols);
1071
+ setShowTableModal(false);
1072
+ };
1073
+ var handleFindReplaceToggle = function (event) {
1074
+ event.preventDefault();
1075
+ setShowFindReplace(!showFindReplace);
1076
+ if (!showFindReplace) {
1077
+ onSearchQueryChange === null || onSearchQueryChange === void 0 ? void 0 : onSearchQueryChange('');
1078
+ setReplaceText('');
1079
+ onCurrentMatchIndexChange === null || onCurrentMatchIndexChange === void 0 ? void 0 : onCurrentMatchIndexChange(0);
1080
+ onSearchMatchesChange === null || onSearchMatchesChange === void 0 ? void 0 : onSearchMatchesChange([]);
1081
+ setTotalMatches(0);
1082
+ }
1083
+ };
1084
+ React.useEffect(function () {
1085
+ if (!searchQuery || !showFindReplace) {
1086
+ onSearchMatchesChange === null || onSearchMatchesChange === void 0 ? void 0 : onSearchMatchesChange([]);
1087
+ setTotalMatches(0);
1088
+ onCurrentMatchIndexChange === null || onCurrentMatchIndexChange === void 0 ? void 0 : onCurrentMatchIndexChange(0);
1089
+ return;
1090
+ }
1091
+ var matches = findAllMatches(editor, searchQuery);
1092
+ onSearchMatchesChange === null || onSearchMatchesChange === void 0 ? void 0 : onSearchMatchesChange(matches);
1093
+ setTotalMatches(matches.length);
1094
+ if (matches.length > 0) {
1095
+ onCurrentMatchIndexChange === null || onCurrentMatchIndexChange === void 0 ? void 0 : onCurrentMatchIndexChange(0);
1096
+ navigateToMatch(editor, matches[0]);
1097
+ }
1098
+ else {
1099
+ onCurrentMatchIndexChange === null || onCurrentMatchIndexChange === void 0 ? void 0 : onCurrentMatchIndexChange(0);
1100
+ }
1101
+ }, [searchQuery, showFindReplace, editor, onSearchMatchesChange, onCurrentMatchIndexChange]);
1102
+ var handleNextMatch = function () {
1103
+ if (searchMatches.length === 0)
1104
+ return;
1105
+ var nextIndex = (currentMatchIndex + 1) % searchMatches.length;
1106
+ onCurrentMatchIndexChange === null || onCurrentMatchIndexChange === void 0 ? void 0 : onCurrentMatchIndexChange(nextIndex);
1107
+ navigateToMatch(editor, searchMatches[nextIndex]);
1108
+ };
1109
+ var handlePrevMatch = function () {
1110
+ if (searchMatches.length === 0)
1111
+ return;
1112
+ var prevIndex = currentMatchIndex === 0 ? searchMatches.length - 1 : currentMatchIndex - 1;
1113
+ onCurrentMatchIndexChange === null || onCurrentMatchIndexChange === void 0 ? void 0 : onCurrentMatchIndexChange(prevIndex);
1114
+ navigateToMatch(editor, searchMatches[prevIndex]);
1115
+ };
1116
+ var handleReplace = function () {
1117
+ if (searchMatches.length === 0 || currentMatchIndex >= searchMatches.length)
1118
+ return;
1119
+ replaceMatch(editor, searchMatches[currentMatchIndex], replaceText);
1120
+ var matches = findAllMatches(editor, searchQuery);
1121
+ onSearchMatchesChange === null || onSearchMatchesChange === void 0 ? void 0 : onSearchMatchesChange(matches);
1122
+ };
1123
+ var handleReplaceAll = function () {
1124
+ if (searchMatches.length === 0)
1125
+ return;
1126
+ replaceAllMatches(editor, searchMatches, replaceText);
1127
+ onSearchQueryChange === null || onSearchQueryChange === void 0 ? void 0 : onSearchQueryChange('');
1128
+ setTimeout(function () {
1129
+ onSearchQueryChange === null || onSearchQueryChange === void 0 ? void 0 : onSearchQueryChange('');
1130
+ setReplaceText('');
1131
+ onSearchMatchesChange === null || onSearchMatchesChange === void 0 ? void 0 : onSearchMatchesChange([]);
1132
+ setTotalMatches(0);
1133
+ onCurrentMatchIndexChange === null || onCurrentMatchIndexChange === void 0 ? void 0 : onCurrentMatchIndexChange(0);
1134
+ }, 50);
1135
+ };
1136
+ React.useEffect(function () {
1137
+ var handleExternalEdit = function (linkData) {
1138
+ setLinkText(linkData.text);
1139
+ setLinkUrl(linkData.url);
1140
+ setLinkTitle(linkData.title || '');
1141
+ setLinkTarget(linkData.target || '_self');
1142
+ setIsEditingLink(true);
1143
+ setShowLinkModal(true);
1144
+ if (linkData.path) {
1145
+ editor.selection = Editor.range(editor, linkData.path);
1146
+ }
1147
+ };
1148
+ window.__editiumLinkEditHandler = handleExternalEdit;
1149
+ return function () {
1150
+ delete window.__editiumLinkEditHandler;
1151
+ };
1152
+ }, [editor]);
1153
+ React.useEffect(function () {
1154
+ var handleImageReplace = function (imageData) {
1155
+ setImageUrl(imageData.url);
1156
+ setImageAlt(imageData.alt || '');
1157
+ setImageFile(null);
1158
+ setImageUploadError('');
1159
+ setIsReplacingImage(true);
1160
+ setReplacingImagePath(imageData.path);
1161
+ setShowImageModal(true);
1162
+ };
1163
+ window.__editiumImageReplaceHandler = handleImageReplace;
1164
+ return function () {
1165
+ delete window.__editiumImageReplaceHandler;
1166
+ };
1167
+ }, []);
1168
+ var blockFormattingItems = ['paragraph', 'heading-one', 'heading-two', 'heading-three', 'heading-four', 'heading-five', 'heading-six', 'heading-seven', 'heading-eight'];
1169
+ var alignmentItems = ['left', 'center', 'right', 'justify'];
1170
+ var formatItems = ['bold', 'italic', 'underline', 'strikethrough', 'code', 'superscript', 'subscript'];
1171
+ var listItems = ['bulleted-list', 'numbered-list', 'indent', 'outdent'];
1172
+ var blockItems = ['blockquote', 'code-block'];
1173
+ var colorItems = ['text-color', 'bg-color'];
1174
+ var insertItems = ['link', 'horizontal-rule', 'image', 'table'];
1175
+ var editItems = ['undo', 'redo'];
1176
+ var colorPalette = [
1177
+ { name: 'Black', value: '#000000' },
1178
+ { name: 'Dark Gray', value: '#495057' },
1179
+ { name: 'Gray', value: '#6c757d' },
1180
+ { name: 'Light Gray', value: '#adb5bd' },
1181
+ { name: 'Red', value: '#dc3545' },
1182
+ { name: 'Orange', value: '#fd7e14' },
1183
+ { name: 'Yellow', value: '#ffc107' },
1184
+ { name: 'Green', value: '#28a745' },
1185
+ { name: 'Teal', value: '#20c997' },
1186
+ { name: 'Blue', value: '#007bff' },
1187
+ { name: 'Indigo', value: '#6610f2' },
1188
+ { name: 'Purple', value: '#6f42c1' },
1189
+ { name: 'Pink', value: '#e83e8c' },
1190
+ { name: 'White', value: '#ffffff' },
1191
+ ];
1192
+ var renderToolbarItem = function (item, index) {
1193
+ if (item === 'separator') {
1194
+ var prevItem = index > 0 ? items[index - 1] : null;
1195
+ if (prevItem) {
1196
+ if (formatItems.includes(prevItem)) {
1197
+ var firstFormatIndex = items.findIndex(function (i) { return formatItems.includes(i); });
1198
+ if (firstFormatIndex !== index - 1)
1199
+ return null;
1200
+ }
1201
+ if (listItems.includes(prevItem)) {
1202
+ var firstListIndex = items.findIndex(function (i) { return listItems.includes(i); });
1203
+ if (firstListIndex !== index - 1)
1204
+ return null;
1205
+ }
1206
+ if (alignmentItems.includes(prevItem)) {
1207
+ var firstAlignIndex = items.findIndex(function (i) { return alignmentItems.includes(i); });
1208
+ if (firstAlignIndex !== index - 1)
1209
+ return null;
1210
+ }
1211
+ if (blockFormattingItems.includes(prevItem)) {
1212
+ var firstBlockIndex = items.findIndex(function (i) { return blockFormattingItems.includes(i); });
1213
+ if (firstBlockIndex !== index - 1)
1214
+ return null;
1215
+ }
1216
+ if (insertItems.includes(prevItem)) {
1217
+ var firstInsertIndex = items.findIndex(function (i) { return insertItems.includes(i); });
1218
+ if (firstInsertIndex !== index - 1)
1219
+ return null;
1220
+ }
1221
+ if (editItems.includes(prevItem)) {
1222
+ var firstEditIndex = items.findIndex(function (i) { return editItems.includes(i); });
1223
+ if (firstEditIndex !== index - 1)
1224
+ return null;
1225
+ }
1226
+ }
1227
+ return jsx(ToolbarSeparator, {}, "separator-".concat(index));
1228
+ }
1229
+ if (blockFormattingItems.includes(item)) {
1230
+ var firstBlockIndex = items.findIndex(function (i) { return blockFormattingItems.includes(i); });
1231
+ var currentIndex = items.findIndex(function (i) { return i === item; });
1232
+ if (firstBlockIndex !== currentIndex) {
1233
+ return null; // Skip rendering individual block formatting buttons
1234
+ }
1235
+ var activeBlock = blockFormattingItems.find(function (block) {
1236
+ return items.includes(block) && isBlockActive(editor, block);
1237
+ });
1238
+ var getBlockLabel_1 = function (block) {
1239
+ switch (block) {
1240
+ case 'paragraph': return 'Paragraph';
1241
+ case 'heading-one': return 'Heading 1';
1242
+ case 'heading-two': return 'Heading 2';
1243
+ case 'heading-three': return 'Heading 3';
1244
+ case 'heading-four': return 'Heading 4';
1245
+ case 'heading-five': return 'Heading 5';
1246
+ case 'heading-six': return 'Heading 6';
1247
+ case 'heading-seven': return 'Heading 7';
1248
+ case 'heading-eight': return 'Heading 8';
1249
+ default: return 'Format';
1250
+ }
1251
+ };
1252
+ return (jsx(Dropdown, { trigger: jsx("span", { children: activeBlock ? getBlockLabel_1(activeBlock) : 'Paragraph' }), title: "Block format", children: items.filter(function (i) { return blockFormattingItems.includes(i); }).map(function (block) { return (jsx(DropdownItem, { active: isBlockActive(editor, block), onMouseDown: function (e) { return handleBlockToggle(e, block); }, children: getBlockLabel_1(block) }, block)); }) }, "block-formatting-dropdown"));
1253
+ }
1254
+ if (alignmentItems.includes(item)) {
1255
+ var firstAlignIndex = items.findIndex(function (i) { return alignmentItems.includes(i); });
1256
+ var currentIndex = items.findIndex(function (i) { return i === item; });
1257
+ if (firstAlignIndex !== currentIndex) {
1258
+ return null; // Skip rendering individual alignment buttons
1259
+ }
1260
+ alignmentItems.find(function (align) {
1261
+ return items.includes(align) && isAlignmentActive(editor, align);
1262
+ });
1263
+ var getAlignmentIcon_1 = function (align) {
1264
+ switch (align) {
1265
+ case 'left':
1266
+ return (jsxs("div", { style: { display: 'flex', flexDirection: 'column', gap: '1px', width: '16px', height: '16px' }, children: [jsx("div", { style: { width: '12px', height: '2px', backgroundColor: 'currentColor' } }), jsx("div", { style: { width: '8px', height: '2px', backgroundColor: 'currentColor' } }), jsx("div", { style: { width: '10px', height: '2px', backgroundColor: 'currentColor' } })] }));
1267
+ case 'center':
1268
+ return (jsxs("div", { style: { display: 'flex', flexDirection: 'column', gap: '1px', width: '16px', height: '16px', alignItems: 'center' }, children: [jsx("div", { style: { width: '10px', height: '2px', backgroundColor: 'currentColor' } }), jsx("div", { style: { width: '6px', height: '2px', backgroundColor: 'currentColor' } }), jsx("div", { style: { width: '8px', height: '2px', backgroundColor: 'currentColor' } })] }));
1269
+ case 'right':
1270
+ return (jsxs("div", { style: { display: 'flex', flexDirection: 'column', gap: '1px', width: '16px', height: '16px', alignItems: 'flex-end' }, children: [jsx("div", { style: { width: '12px', height: '2px', backgroundColor: 'currentColor' } }), jsx("div", { style: { width: '8px', height: '2px', backgroundColor: 'currentColor' } }), jsx("div", { style: { width: '10px', height: '2px', backgroundColor: 'currentColor' } })] }));
1271
+ case 'justify':
1272
+ return (jsxs("div", { style: { display: 'flex', flexDirection: 'column', gap: '1px', width: '16px', height: '16px' }, children: [jsx("div", { style: { width: '100%', height: '2px', backgroundColor: 'currentColor' } }), jsx("div", { style: { width: '100%', height: '2px', backgroundColor: 'currentColor' } }), jsx("div", { style: { width: '100%', height: '2px', backgroundColor: 'currentColor' } })] }));
1273
+ default:
1274
+ return (jsxs("div", { style: { display: 'flex', flexDirection: 'column', gap: '1px', width: '16px', height: '16px' }, children: [jsx("div", { style: { width: '12px', height: '2px', backgroundColor: 'currentColor' } }), jsx("div", { style: { width: '8px', height: '2px', backgroundColor: 'currentColor' } }), jsx("div", { style: { width: '10px', height: '2px', backgroundColor: 'currentColor' } })] }));
1275
+ }
1276
+ };
1277
+ var getAlignmentLabel_1 = function (align) {
1278
+ switch (align) {
1279
+ case 'left': return 'Align Left';
1280
+ case 'center': return 'Align Center';
1281
+ case 'right': return 'Align Right';
1282
+ case 'justify': return 'Justify';
1283
+ default: return 'Align';
1284
+ }
1285
+ };
1286
+ return (jsx(Dropdown, { trigger: jsx("span", { children: "Align" }), title: "Text alignment", children: items.filter(function (i) { return alignmentItems.includes(i); }).map(function (align) { return (jsx(DropdownItem, { active: isAlignmentActive(editor, align), onMouseDown: function (e) { return handleAlignmentToggle(e, align); }, icon: getAlignmentIcon_1(align), children: getAlignmentLabel_1(align) }, align)); }) }, "alignment-dropdown"));
1287
+ }
1288
+ switch (item) {
1289
+ case 'bold':
1290
+ case 'italic':
1291
+ case 'underline':
1292
+ case 'strikethrough':
1293
+ case 'code':
1294
+ case 'superscript':
1295
+ case 'subscript': {
1296
+ var formatItems_1 = ['bold', 'italic', 'underline', 'strikethrough', 'code', 'superscript', 'subscript'];
1297
+ var firstFormatIndex = items.findIndex(function (i) { return formatItems_1.includes(i); });
1298
+ var currentIndex = items.findIndex(function (i) { return i === item; });
1299
+ if (firstFormatIndex !== currentIndex)
1300
+ return null;
1301
+ return (jsxs(Dropdown, { trigger: jsx("span", { children: "Format" }), title: "Format", children: [items.includes('bold') && (jsx(DropdownItem, { active: isMarkActive(editor, 'bold'), onMouseDown: function (e) { return handleMarkToggle(e, 'bold'); }, icon: jsx("span", { style: { fontWeight: 'bold', fontSize: '16px' }, children: "B" }), children: "Bold" })), items.includes('italic') && (jsx(DropdownItem, { active: isMarkActive(editor, 'italic'), onMouseDown: function (e) { return handleMarkToggle(e, 'italic'); }, icon: jsx("span", { style: { fontStyle: 'italic', fontSize: '16px' }, children: "I" }), children: "Italic" })), items.includes('underline') && (jsx(DropdownItem, { active: isMarkActive(editor, 'underline'), onMouseDown: function (e) { return handleMarkToggle(e, 'underline'); }, icon: jsx("span", { style: { textDecoration: 'underline', fontSize: '16px' }, children: "U" }), children: "Underline" })), items.includes('strikethrough') && (jsx(DropdownItem, { active: isMarkActive(editor, 'strikethrough'), onMouseDown: function (e) { return handleMarkToggle(e, 'strikethrough'); }, icon: jsx("span", { style: { textDecoration: 'line-through', fontSize: '16px' }, children: "S" }), children: "Strikethrough" })), items.includes('code') && (jsx(DropdownItem, { active: isMarkActive(editor, 'code'), onMouseDown: function (e) { return handleMarkToggle(e, 'code'); }, icon: jsx(CodeBracketIcon, { style: { width: '16px', height: '16px' } }), children: "Code" })), items.includes('superscript') && (jsx(DropdownItem, { active: isMarkActive(editor, 'superscript'), onMouseDown: function (e) { return handleMarkToggle(e, 'superscript'); }, icon: jsxs("span", { style: { fontSize: '12px' }, children: ["X", jsx("sup", { children: "2" })] }), children: "Superscript" })), items.includes('subscript') && (jsx(DropdownItem, { active: isMarkActive(editor, 'subscript'), onMouseDown: function (e) { return handleMarkToggle(e, 'subscript'); }, icon: jsxs("span", { style: { fontSize: '12px' }, children: ["X", jsx("sub", { children: "2" })] }), children: "Subscript" }))] }, "format-menu"));
1302
+ }
1303
+ case 'bulleted-list':
1304
+ case 'numbered-list':
1305
+ case 'indent':
1306
+ case 'outdent': {
1307
+ var listItems_1 = ['bulleted-list', 'numbered-list', 'indent', 'outdent'];
1308
+ var firstListIndex = items.findIndex(function (i) { return listItems_1.includes(i); });
1309
+ var currentIndex = items.findIndex(function (i) { return i === item; });
1310
+ if (firstListIndex !== currentIndex)
1311
+ return null;
1312
+ return (jsxs(Dropdown, { trigger: jsx("span", { children: "Lists" }), title: "Lists", children: [items.includes('bulleted-list') && (jsx(DropdownItem, { active: isBlockActive(editor, 'bulleted-list'), onMouseDown: function (e) { return handleBlockToggle(e, 'bulleted-list'); }, icon: jsx(ListBulletIcon, { style: { width: '16px', height: '16px' } }), children: "Bullet list" })), items.includes('numbered-list') && (jsx(DropdownItem, { active: isBlockActive(editor, 'numbered-list'), onMouseDown: function (e) { return handleBlockToggle(e, 'numbered-list'); }, icon: jsx("span", { style: { fontSize: '14px', fontWeight: '600' }, children: "1." }), children: "Numbered list" })), items.includes('indent') && (jsx(DropdownItem, { active: false, onMouseDown: handleIndent, icon: jsx(ArrowRightIcon, { style: { width: '16px', height: '16px' } }), children: "Increase indent" })), items.includes('outdent') && (jsx(DropdownItem, { active: false, onMouseDown: handleOutdent, icon: jsx(ArrowLeftIcon, { style: { width: '16px', height: '16px' } }), children: "Decrease indent" }))] }, "lists-menu"));
1313
+ }
1314
+ case 'blockquote':
1315
+ case 'code-block': {
1316
+ var firstBlockItemIndex = items.findIndex(function (i) { return blockItems.includes(i); });
1317
+ var currentIndex = items.findIndex(function (i) { return i === item; });
1318
+ if (firstBlockItemIndex !== currentIndex)
1319
+ return null;
1320
+ return (jsxs(Dropdown, { trigger: jsx("span", { children: "Blocks" }), title: "Blocks", children: [items.includes('blockquote') && (jsx(DropdownItem, { active: isBlockActive(editor, 'blockquote'), onMouseDown: function (e) { return handleBlockToggle(e, 'blockquote'); }, icon: jsx("span", { style: { fontSize: '16px', fontWeight: 'bold' }, children: "\u275D" }), children: "Blockquote" })), items.includes('code-block') && (jsx(DropdownItem, { active: isBlockActive(editor, 'code-block'), onMouseDown: function (e) { return handleBlockToggle(e, 'code-block'); }, icon: jsx(CodeBracketIcon, { style: { width: '16px', height: '16px' } }), children: "Code Block" }))] }, "blocks-menu"));
1321
+ }
1322
+ case 'text-color':
1323
+ case 'bg-color': {
1324
+ var firstColorIndex = items.findIndex(function (i) { return colorItems.includes(i); });
1325
+ var currentIndex = items.findIndex(function (i) { return i === item; });
1326
+ if (firstColorIndex !== currentIndex)
1327
+ return null;
1328
+ var activeTextColor_1 = getActiveColor(editor);
1329
+ var activeBgColor_1 = getActiveBackgroundColor(editor);
1330
+ return (jsxs(Dropdown, { trigger: jsx("span", { children: "Color" }), title: "Color", children: [items.includes('text-color') && (jsxs("div", { style: { padding: '8px 12px' }, children: [jsx("div", { style: {
1331
+ fontSize: '12px',
1332
+ fontWeight: '600',
1333
+ marginBottom: '8px',
1334
+ color: '#495057'
1335
+ }, children: "Text Color" }), jsx("div", { style: {
1336
+ display: 'grid',
1337
+ gridTemplateColumns: 'repeat(7, 1fr)',
1338
+ gap: '4px',
1339
+ marginBottom: '8px'
1340
+ }, children: colorPalette.map(function (color) { return (jsx("button", { onMouseDown: function (e) {
1341
+ e.preventDefault();
1342
+ applyColor(editor, color.value);
1343
+ }, title: color.name, style: {
1344
+ width: '24px',
1345
+ height: '24px',
1346
+ backgroundColor: color.value,
1347
+ border: activeTextColor_1 === color.value ? '2px solid #007bff' : '1px solid #dee2e6',
1348
+ borderRadius: '3px',
1349
+ cursor: 'pointer',
1350
+ padding: 0,
1351
+ boxShadow: color.value === '#ffffff' ? 'inset 0 0 0 1px #dee2e6' : 'none'
1352
+ } }, "text-".concat(color.value))); }) }), jsxs("div", { style: {
1353
+ display: 'flex',
1354
+ alignItems: 'center',
1355
+ gap: '6px',
1356
+ marginBottom: '8px',
1357
+ paddingTop: '4px'
1358
+ }, children: [jsx("input", { type: "color", value: activeTextColor_1 || '#000000', onChange: function (e) {
1359
+ applyColor(editor, e.target.value);
1360
+ }, title: "Pick custom color", style: {
1361
+ width: '24px',
1362
+ height: '24px',
1363
+ border: '1px solid #dee2e6',
1364
+ borderRadius: '3px',
1365
+ cursor: 'pointer',
1366
+ padding: '0',
1367
+ backgroundColor: 'transparent'
1368
+ } }), jsx("span", { style: {
1369
+ fontSize: '12px',
1370
+ color: '#6c757d'
1371
+ }, children: "Custom" })] }), jsx("button", { onMouseDown: function (e) {
1372
+ e.preventDefault();
1373
+ applyColor(editor, null);
1374
+ }, style: {
1375
+ width: '100%',
1376
+ padding: '4px 8px',
1377
+ fontSize: '12px',
1378
+ border: '1px solid #dee2e6',
1379
+ borderRadius: '3px',
1380
+ backgroundColor: 'transparent',
1381
+ cursor: 'pointer',
1382
+ color: '#495057'
1383
+ }, children: "Remove Color" })] })), items.includes('bg-color') && (jsxs("div", { style: { padding: '8px 12px', borderTop: '1px solid #dee2e6' }, children: [jsx("div", { style: {
1384
+ fontSize: '12px',
1385
+ fontWeight: '600',
1386
+ marginBottom: '8px',
1387
+ color: '#495057'
1388
+ }, children: "Background Highlight" }), jsx("div", { style: {
1389
+ display: 'grid',
1390
+ gridTemplateColumns: 'repeat(7, 1fr)',
1391
+ gap: '4px',
1392
+ marginBottom: '8px'
1393
+ }, children: colorPalette.map(function (color) { return (jsx("button", { onMouseDown: function (e) {
1394
+ e.preventDefault();
1395
+ applyBackgroundColor(editor, color.value);
1396
+ }, title: color.name, style: {
1397
+ width: '24px',
1398
+ height: '24px',
1399
+ backgroundColor: color.value,
1400
+ border: activeBgColor_1 === color.value ? '2px solid #007bff' : '1px solid #dee2e6',
1401
+ borderRadius: '3px',
1402
+ cursor: 'pointer',
1403
+ padding: 0,
1404
+ boxShadow: color.value === '#ffffff' ? 'inset 0 0 0 1px #dee2e6' : 'none'
1405
+ } }, "bg-".concat(color.value))); }) }), jsxs("div", { style: {
1406
+ display: 'flex',
1407
+ alignItems: 'center',
1408
+ gap: '6px',
1409
+ marginBottom: '8px',
1410
+ paddingTop: '4px'
1411
+ }, children: [jsx("input", { type: "color", value: activeBgColor_1 || '#ffffff', onChange: function (e) {
1412
+ applyBackgroundColor(editor, e.target.value);
1413
+ }, title: "Pick custom color", style: {
1414
+ width: '24px',
1415
+ height: '24px',
1416
+ border: '1px solid #dee2e6',
1417
+ borderRadius: '3px',
1418
+ cursor: 'pointer',
1419
+ padding: '0',
1420
+ backgroundColor: 'transparent'
1421
+ } }), jsx("span", { style: {
1422
+ fontSize: '12px',
1423
+ color: '#6c757d'
1424
+ }, children: "Custom" })] }), jsx("button", { onMouseDown: function (e) {
1425
+ e.preventDefault();
1426
+ applyBackgroundColor(editor, null);
1427
+ }, style: {
1428
+ width: '100%',
1429
+ padding: '4px 8px',
1430
+ fontSize: '12px',
1431
+ border: '1px solid #dee2e6',
1432
+ borderRadius: '3px',
1433
+ backgroundColor: 'transparent',
1434
+ cursor: 'pointer',
1435
+ color: '#495057'
1436
+ }, children: "Remove Highlight" })] }))] }, "color-menu"));
1437
+ }
1438
+ case 'link':
1439
+ case 'horizontal-rule':
1440
+ case 'image':
1441
+ case 'table': {
1442
+ var firstInsertIndex = items.findIndex(function (i) { return insertItems.includes(i); });
1443
+ var currentIndex = items.findIndex(function (i) { return i === item; });
1444
+ if (firstInsertIndex !== currentIndex)
1445
+ return null;
1446
+ return (jsxs(Dropdown, { trigger: jsx("span", { children: "Insert" }), title: "Insert", children: [items.includes('link') && (jsx(DropdownItem, { active: isLinkActive(editor), onMouseDown: handleLinkToggle, icon: jsx(LinkIcon, { style: { width: '16px', height: '16px' } }), children: "Link" })), items.includes('image') && (jsx(DropdownItem, { active: false, onMouseDown: handleImageToggle, icon: jsx(PhotoIcon, { style: { width: '16px', height: '16px' } }), children: "Image" })), items.includes('table') && (jsx(DropdownItem, { active: false, onMouseDown: handleTableToggle, icon: jsx(TableCellsIcon, { style: { width: '16px', height: '16px' } }), children: "Table" })), items.includes('horizontal-rule') && (jsx(DropdownItem, { active: false, onMouseDown: function (e) {
1447
+ e.preventDefault();
1448
+ insertHorizontalRule(editor);
1449
+ }, icon: jsx("span", { style: { fontSize: '16px', fontWeight: 'bold' }, children: "\u2015" }), children: "Horizontal Rule" }))] }, "insert-menu"));
1450
+ }
1451
+ case 'undo':
1452
+ case 'redo': {
1453
+ var firstEditIndex = items.findIndex(function (i) { return editItems.includes(i); });
1454
+ var currentIndex = items.findIndex(function (i) { return i === item; });
1455
+ if (firstEditIndex !== currentIndex)
1456
+ return null;
1457
+ return (jsxs(Dropdown, { trigger: jsx("span", { children: "Edit" }), title: "Edit", children: [items.includes('undo') && (jsx(DropdownItem, { active: false, onMouseDown: handleUndo, icon: jsx(ArrowUturnLeftIcon, { style: { width: '16px', height: '16px' } }), children: "Undo" })), items.includes('redo') && (jsx(DropdownItem, { active: false, onMouseDown: handleRedo, icon: jsx(ArrowUturnRightIcon, { style: { width: '16px', height: '16px' } }), children: "Redo" }))] }, "edit-menu"));
1458
+ }
1459
+ case 'view-output':
1460
+ return (jsxs(Dropdown, { trigger: jsx("span", { children: "View" }), title: "View Output", children: [jsx(DropdownItem, { active: false, onMouseDown: function (event) {
1461
+ event.preventDefault();
1462
+ if (onViewOutput) {
1463
+ onViewOutput('preview');
1464
+ }
1465
+ }, icon: jsx(ArrowTopRightOnSquareIcon, { style: { width: '16px', height: '16px' } }), children: "Preview" }), jsx(DropdownItem, { active: false, onMouseDown: function (event) {
1466
+ event.preventDefault();
1467
+ if (onViewOutput) {
1468
+ onViewOutput('html');
1469
+ }
1470
+ }, icon: jsx("span", { style: { fontFamily: 'monospace', fontSize: '14px' }, children: "</>" }), children: "View HTML" }), jsx(DropdownItem, { active: false, onMouseDown: function (event) {
1471
+ event.preventDefault();
1472
+ if (onViewOutput) {
1473
+ onViewOutput('json');
1474
+ }
1475
+ }, icon: jsx("span", { style: { fontFamily: 'monospace', fontSize: '14px' } }), children: "View JSON" })] }, item));
1476
+ case 'find-replace':
1477
+ return (jsx(ToolbarButton, { active: showFindReplace, onMouseDown: handleFindReplaceToggle, title: "Find & Replace", children: jsx(MagnifyingGlassIcon, { style: { width: '18px', height: '18px' } }) }, item));
1478
+ case 'fullscreen':
1479
+ return (jsx(ToolbarButton, { active: isFullscreen, onMouseDown: function (e) {
1480
+ e.preventDefault();
1481
+ onFullscreenToggle === null || onFullscreenToggle === void 0 ? void 0 : onFullscreenToggle();
1482
+ }, title: isFullscreen ? "Exit Fullscreen (Esc)" : "Enter Fullscreen (F11)", children: isFullscreen ? (jsx(ArrowsPointingInIcon, { style: { width: '18px', height: '18px' } })) : (jsx(ArrowsPointingOutIcon, { style: { width: '18px', height: '18px' } })) }, item));
1483
+ default:
1484
+ return null;
1485
+ }
1486
+ };
1487
+ return (jsxs(Fragment, { children: [showLinkModal && (jsx("div", { style: {
1488
+ position: 'fixed',
1489
+ top: 0,
1490
+ left: 0,
1491
+ right: 0,
1492
+ bottom: 0,
1493
+ backgroundColor: 'rgba(0, 0, 0, 0.5)',
1494
+ display: 'flex',
1495
+ alignItems: 'center',
1496
+ justifyContent: 'center',
1497
+ zIndex: 10000,
1498
+ }, onClick: function () {
1499
+ setShowLinkModal(false);
1500
+ setLinkText('');
1501
+ setLinkUrl('');
1502
+ setLinkTitle('');
1503
+ setLinkTarget('_self');
1504
+ setIsEditingLink(false);
1505
+ }, children: jsxs("div", { style: {
1506
+ backgroundColor: '#ffffff',
1507
+ borderRadius: '8px',
1508
+ padding: '24px',
1509
+ width: '90%',
1510
+ maxWidth: '500px',
1511
+ boxShadow: '0 20px 25px -5px rgba(0, 0, 0, 0.1), 0 10px 10px -5px rgba(0, 0, 0, 0.04)',
1512
+ }, onClick: function (e) { return e.stopPropagation(); }, children: [jsx("h3", { style: { margin: '0 0 20px 0', color: '#111827', fontSize: '20px', fontWeight: '600' }, children: isEditingLink ? 'Edit Link' : 'Insert Link' }), jsxs("div", { style: { marginBottom: '16px' }, children: [jsx("label", { style: { display: 'block', marginBottom: '8px', color: '#374151', fontSize: '14px', fontWeight: '500' }, children: "Text to display" }), jsx("input", { type: "text", value: linkText, onChange: function (e) { return setLinkText(e.target.value); }, placeholder: "Enter link text", style: {
1513
+ width: '100%',
1514
+ padding: '8px 12px',
1515
+ border: '1px solid #d1d5db',
1516
+ borderRadius: '6px',
1517
+ fontSize: '14px',
1518
+ outline: 'none',
1519
+ boxSizing: 'border-box',
1520
+ }, onFocus: function (e) { return e.target.style.borderColor = '#3b82f6'; }, onBlur: function (e) { return e.target.style.borderColor = '#d1d5db'; } }), jsx("small", { style: { display: 'block', marginTop: '4px', color: '#6b7280', fontSize: '12px' }, children: "If empty, will use URL or selected text as display text" })] }), jsxs("div", { style: { marginBottom: '16px' }, children: [jsxs("label", { style: { display: 'block', marginBottom: '8px', color: '#374151', fontSize: '14px', fontWeight: '500' }, children: ["URL ", jsx("span", { style: { color: '#ef4444' }, children: "*" })] }), jsx("input", { type: "url", value: linkUrl, onChange: function (e) { return setLinkUrl(e.target.value); }, placeholder: "https://example.com", style: {
1521
+ width: '100%',
1522
+ padding: '8px 12px',
1523
+ border: '1px solid #d1d5db',
1524
+ borderRadius: '6px',
1525
+ fontSize: '14px',
1526
+ outline: 'none',
1527
+ boxSizing: 'border-box',
1528
+ }, onFocus: function (e) { return e.target.style.borderColor = '#3b82f6'; }, onBlur: function (e) { return e.target.style.borderColor = '#d1d5db'; }, onKeyDown: function (e) {
1529
+ if (e.key === 'Enter') {
1530
+ e.preventDefault();
1531
+ handleInsertLink();
1532
+ }
1533
+ } })] }), jsxs("div", { style: { marginBottom: '16px' }, children: [jsx("label", { style: { display: 'block', marginBottom: '8px', color: '#374151', fontSize: '14px', fontWeight: '500' }, children: "Title" }), jsx("input", { type: "text", value: linkTitle, onChange: function (e) { return setLinkTitle(e.target.value); }, placeholder: "Link title (tooltip)", style: {
1534
+ width: '100%',
1535
+ padding: '8px 12px',
1536
+ border: '1px solid #d1d5db',
1537
+ borderRadius: '6px',
1538
+ fontSize: '14px',
1539
+ outline: 'none',
1540
+ boxSizing: 'border-box',
1541
+ }, onFocus: function (e) { return e.target.style.borderColor = '#3b82f6'; }, onBlur: function (e) { return e.target.style.borderColor = '#d1d5db'; } }), jsx("small", { style: { display: 'block', marginTop: '4px', color: '#6b7280', fontSize: '12px' }, children: "Appears as a tooltip when hovering over the link" })] }), jsxs("div", { style: { marginBottom: '24px' }, children: [jsx("label", { style: { display: 'block', marginBottom: '8px', color: '#374151', fontSize: '14px', fontWeight: '500' }, children: "Open link in" }), jsxs("div", { style: { display: 'flex', gap: '12px' }, children: [jsxs("label", { style: { display: 'flex', alignItems: 'center', cursor: 'pointer' }, children: [jsx("input", { type: "radio", name: "linkTarget", value: "_self", checked: linkTarget === '_self', onChange: function (e) { return setLinkTarget(e.target.value); }, style: { marginRight: '6px', cursor: 'pointer' } }), jsx("span", { style: { fontSize: '14px', color: '#374151' }, children: "Current tab" })] }), jsxs("label", { style: { display: 'flex', alignItems: 'center', cursor: 'pointer' }, children: [jsx("input", { type: "radio", name: "linkTarget", value: "_blank", checked: linkTarget === '_blank', onChange: function (e) { return setLinkTarget(e.target.value); }, style: { marginRight: '6px', cursor: 'pointer' } }), jsx("span", { style: { fontSize: '14px', color: '#374151' }, children: "New tab" })] })] })] }), jsxs("div", { style: { display: 'flex', gap: '12px', justifyContent: 'flex-end' }, children: [jsx("button", { onClick: function () {
1542
+ setShowLinkModal(false);
1543
+ setLinkText('');
1544
+ setLinkUrl('');
1545
+ setLinkTitle('');
1546
+ setLinkTarget('_self');
1547
+ setIsEditingLink(false);
1548
+ }, style: {
1549
+ padding: '8px 16px',
1550
+ border: '1px solid #d1d5db',
1551
+ borderRadius: '6px',
1552
+ backgroundColor: '#ffffff',
1553
+ color: '#374151',
1554
+ fontSize: '14px',
1555
+ fontWeight: '500',
1556
+ cursor: 'pointer',
1557
+ transition: 'all 0.15s ease',
1558
+ }, onMouseEnter: function (e) { return e.currentTarget.style.backgroundColor = '#f9fafb'; }, onMouseLeave: function (e) { return e.currentTarget.style.backgroundColor = '#ffffff'; }, children: "Cancel" }), jsx("button", { onClick: handleInsertLink, style: {
1559
+ padding: '8px 16px',
1560
+ border: 'none',
1561
+ borderRadius: '6px',
1562
+ backgroundColor: '#3b82f6',
1563
+ color: '#ffffff',
1564
+ fontSize: '14px',
1565
+ fontWeight: '500',
1566
+ cursor: 'pointer',
1567
+ transition: 'all 0.15s ease',
1568
+ }, onMouseEnter: function (e) { return e.currentTarget.style.backgroundColor = '#2563eb'; }, onMouseLeave: function (e) { return e.currentTarget.style.backgroundColor = '#3b82f6'; }, children: isEditingLink ? 'Update Link' : 'Insert Link' })] })] }) })), showImageModal && (jsx("div", { style: {
1569
+ position: 'fixed',
1570
+ top: 0,
1571
+ left: 0,
1572
+ right: 0,
1573
+ bottom: 0,
1574
+ backgroundColor: 'rgba(0, 0, 0, 0.5)',
1575
+ display: 'flex',
1576
+ alignItems: 'center',
1577
+ justifyContent: 'center',
1578
+ zIndex: 10000,
1579
+ }, onClick: function () {
1580
+ setShowImageModal(false);
1581
+ setImageUrl('');
1582
+ setImageAlt('');
1583
+ setImageFile(null);
1584
+ setImageUploadError('');
1585
+ }, children: jsxs("div", { style: {
1586
+ backgroundColor: '#ffffff',
1587
+ borderRadius: '8px',
1588
+ padding: '24px',
1589
+ width: '90%',
1590
+ maxWidth: '500px',
1591
+ boxShadow: '0 20px 25px -5px rgba(0, 0, 0, 0.1), 0 10px 10px -5px rgba(0, 0, 0, 0.04)',
1592
+ }, onClick: function (e) { return e.stopPropagation(); }, children: [jsx("h3", { style: { margin: '0 0 20px 0', color: '#111827', fontSize: '20px', fontWeight: '600' }, children: isReplacingImage ? 'Replace Image' : 'Insert Image' }), jsxs("div", { style: { marginBottom: '16px' }, children: [jsx("label", { style: { display: 'block', marginBottom: '8px', color: '#374151', fontSize: '14px', fontWeight: '500' }, children: "Image URL" }), jsx("input", { type: "url", value: imageUrl, onChange: function (e) { return setImageUrl(e.target.value); }, placeholder: "https://example.com/image.jpg", disabled: !!imageFile, style: {
1593
+ width: '100%',
1594
+ padding: '8px 12px',
1595
+ border: '1px solid #d1d5db',
1596
+ borderRadius: '6px',
1597
+ fontSize: '14px',
1598
+ outline: 'none',
1599
+ boxSizing: 'border-box',
1600
+ backgroundColor: imageFile ? '#f9fafb' : '#ffffff',
1601
+ }, onFocus: function (e) { return !imageFile && (e.target.style.borderColor = '#3b82f6'); }, onBlur: function (e) { return e.target.style.borderColor = '#d1d5db'; } })] }), jsxs("div", { style: {
1602
+ marginBottom: '16px',
1603
+ padding: '12px',
1604
+ backgroundColor: '#f9fafb',
1605
+ borderRadius: '6px',
1606
+ textAlign: 'center'
1607
+ }, children: [jsx("p", { style: { margin: '0 0 12px 0', color: '#6b7280', fontSize: '14px' }, children: "Or upload from your computer" }), jsx("input", { type: "file", accept: "image/*", onChange: handleFileChange, style: { display: 'none' }, id: "image-upload" }), jsx("label", { htmlFor: "image-upload", style: {
1608
+ display: 'inline-block',
1609
+ padding: '8px 16px',
1610
+ border: '1px solid #d1d5db',
1611
+ borderRadius: '6px',
1612
+ backgroundColor: '#ffffff',
1613
+ color: '#374151',
1614
+ fontSize: '14px',
1615
+ fontWeight: '500',
1616
+ cursor: 'pointer',
1617
+ transition: 'all 0.15s ease',
1618
+ }, onMouseEnter: function (e) { return e.currentTarget.style.backgroundColor = '#f9fafb'; }, onMouseLeave: function (e) { return e.currentTarget.style.backgroundColor = '#ffffff'; }, children: "Choose File" }), imageFile && (jsxs("p", { style: { margin: '8px 0 0 0', color: '#374151', fontSize: '13px' }, children: ["Selected: ", imageFile.name] })), !((_b = window.__editiumProps) === null || _b === void 0 ? void 0 : _b.onImageUpload) && (jsx("p", { style: {
1619
+ margin: '8px 0 0 0',
1620
+ color: '#dc2626',
1621
+ fontSize: '12px',
1622
+ fontStyle: 'italic'
1623
+ }, children: "\u26A0 Upload not configured. Define onImageUpload in your app." }))] }), jsxs("div", { style: { marginBottom: '16px' }, children: [jsx("label", { style: { display: 'block', marginBottom: '8px', color: '#374151', fontSize: '14px', fontWeight: '500' }, children: "Alt Text (optional)" }), jsx("input", { type: "text", value: imageAlt, onChange: function (e) { return setImageAlt(e.target.value); }, placeholder: "Describe the image", style: {
1624
+ width: '100%',
1625
+ padding: '8px 12px',
1626
+ border: '1px solid #d1d5db',
1627
+ borderRadius: '6px',
1628
+ fontSize: '14px',
1629
+ outline: 'none',
1630
+ boxSizing: 'border-box',
1631
+ }, onFocus: function (e) { return e.target.style.borderColor = '#3b82f6'; }, onBlur: function (e) { return e.target.style.borderColor = '#d1d5db'; } }), jsx("small", { style: { display: 'block', marginTop: '4px', color: '#6b7280', fontSize: '12px' }, children: "For accessibility" })] }), imageUploadError && (jsx("div", { style: {
1632
+ marginBottom: '16px',
1633
+ padding: '12px',
1634
+ backgroundColor: '#fef2f2',
1635
+ border: '1px solid #fecaca',
1636
+ borderRadius: '6px',
1637
+ color: '#dc2626',
1638
+ fontSize: '14px'
1639
+ }, children: imageUploadError })), jsxs("div", { style: { display: 'flex', gap: '12px', justifyContent: 'flex-end' }, children: [jsx("button", { onClick: function () {
1640
+ setShowImageModal(false);
1641
+ setImageUrl('');
1642
+ setImageAlt('');
1643
+ setImageFile(null);
1644
+ setImageUploadError('');
1645
+ }, style: {
1646
+ padding: '8px 16px',
1647
+ border: '1px solid #d1d5db',
1648
+ borderRadius: '6px',
1649
+ backgroundColor: '#ffffff',
1650
+ color: '#374151',
1651
+ fontSize: '14px',
1652
+ fontWeight: '500',
1653
+ cursor: 'pointer',
1654
+ transition: 'all 0.15s ease',
1655
+ }, onMouseEnter: function (e) { return e.currentTarget.style.backgroundColor = '#f9fafb'; }, onMouseLeave: function (e) { return e.currentTarget.style.backgroundColor = '#ffffff'; }, children: "Cancel" }), jsx("button", { onClick: handleInsertImage, style: {
1656
+ padding: '8px 16px',
1657
+ border: 'none',
1658
+ borderRadius: '6px',
1659
+ backgroundColor: '#3b82f6',
1660
+ color: '#ffffff',
1661
+ fontSize: '14px',
1662
+ fontWeight: '500',
1663
+ cursor: 'pointer',
1664
+ transition: 'all 0.15s ease',
1665
+ }, onMouseEnter: function (e) { return e.currentTarget.style.backgroundColor = '#2563eb'; }, onMouseLeave: function (e) { return e.currentTarget.style.backgroundColor = '#3b82f6'; }, children: isReplacingImage ? 'Replace' : 'Insert Image' })] })] }) })), showTableModal && (jsx("div", { style: {
1666
+ position: 'fixed',
1667
+ top: 0,
1668
+ left: 0,
1669
+ right: 0,
1670
+ bottom: 0,
1671
+ backgroundColor: 'rgba(0, 0, 0, 0.5)',
1672
+ display: 'flex',
1673
+ alignItems: 'center',
1674
+ justifyContent: 'center',
1675
+ zIndex: 1000,
1676
+ }, children: jsxs("div", { style: {
1677
+ backgroundColor: 'white',
1678
+ borderRadius: '8px',
1679
+ padding: '24px',
1680
+ maxWidth: '400px',
1681
+ width: '90%',
1682
+ boxShadow: '0 4px 20px rgba(0, 0, 0, 0.15)',
1683
+ }, children: [jsx("h3", { style: { margin: '0 0 16px 0', fontSize: '18px', fontWeight: '600', color: '#1f2937' }, children: "Insert Table" }), jsxs("div", { style: { marginBottom: '16px' }, children: [jsx("div", { style: {
1684
+ display: 'grid',
1685
+ gridTemplateColumns: 'repeat(10, 30px)',
1686
+ gridTemplateRows: 'repeat(10, 30px)',
1687
+ gap: '2px',
1688
+ padding: '8px',
1689
+ backgroundColor: '#f9fafb',
1690
+ borderRadius: '4px',
1691
+ width: 'fit-content',
1692
+ }, children: Array.from({ length: 100 }, function (_, index) {
1693
+ var row = Math.floor(index / 10) + 1;
1694
+ var col = (index % 10) + 1;
1695
+ var isHighlighted = row <= tableRows && col <= tableCols;
1696
+ return (jsx("div", { onMouseEnter: function () {
1697
+ setTableRows(row);
1698
+ setTableCols(col);
1699
+ }, onClick: handleInsertTable, style: {
1700
+ width: '30px',
1701
+ height: '30px',
1702
+ border: '1px solid #d1d5db',
1703
+ backgroundColor: isHighlighted ? '#3b82f6' : 'white',
1704
+ cursor: 'pointer',
1705
+ transition: 'background-color 0.1s ease',
1706
+ borderRadius: '2px',
1707
+ } }, index));
1708
+ }) }), jsxs("div", { style: {
1709
+ marginTop: '12px',
1710
+ textAlign: 'center',
1711
+ fontSize: '14px',
1712
+ fontWeight: '500',
1713
+ color: '#374151',
1714
+ }, children: [tableRows, " \u00D7 ", tableCols, " Table"] })] }), jsxs("div", { style: { display: 'flex', gap: '8px', justifyContent: 'flex-end' }, children: [jsx("button", { onClick: function () { return setShowTableModal(false); }, style: {
1715
+ padding: '8px 16px',
1716
+ border: '1px solid #d1d5db',
1717
+ borderRadius: '4px',
1718
+ backgroundColor: 'white',
1719
+ color: '#374151',
1720
+ cursor: 'pointer',
1721
+ fontSize: '14px',
1722
+ fontWeight: '500',
1723
+ }, onMouseEnter: function (e) { return e.currentTarget.style.backgroundColor = '#f3f4f6'; }, onMouseLeave: function (e) { return e.currentTarget.style.backgroundColor = 'white'; }, children: "Cancel" }), jsx("button", { onClick: handleInsertTable, style: {
1724
+ padding: '8px 16px',
1725
+ border: 'none',
1726
+ borderRadius: '4px',
1727
+ backgroundColor: '#3b82f6',
1728
+ color: 'white',
1729
+ cursor: 'pointer',
1730
+ fontSize: '14px',
1731
+ fontWeight: '500',
1732
+ }, onMouseEnter: function (e) { return e.currentTarget.style.backgroundColor = '#2563eb'; }, onMouseLeave: function (e) { return e.currentTarget.style.backgroundColor = '#3b82f6'; }, children: "Insert Table" })] })] }) })), jsxs("div", { className: className, style: {
1733
+ border: '1px solid #ccc',
1734
+ borderBottom: showFindReplace ? 'none' : '1px solid #ccc',
1735
+ padding: '4px 8px',
1736
+ backgroundColor: '#fff',
1737
+ borderRadius: showFindReplace ? '4px 4px 0 0' : '4px',
1738
+ display: 'flex',
1739
+ flexWrap: 'wrap',
1740
+ gap: '2px',
1741
+ alignItems: 'center',
1742
+ justifyContent: 'space-between',
1743
+ boxShadow: 'none',
1744
+ minHeight: '42px',
1745
+ maxWidth: '100%',
1746
+ overflow: 'visible',
1747
+ position: 'relative',
1748
+ zIndex: 100
1749
+ }, children: [jsx("div", { style: { display: 'flex', flexWrap: 'wrap', gap: '2px', alignItems: 'center', flex: 1 }, children: items.filter(function (item) { return item !== 'fullscreen' && item !== 'find-replace'; }).map(function (item, index) { return renderToolbarItem(item, index); }) }), jsxs("div", { style: { display: 'flex', gap: '2px', marginLeft: '8px' }, children: [items.includes('find-replace') && renderToolbarItem('find-replace', items.length - 1), items.includes('fullscreen') && renderToolbarItem('fullscreen', items.length)] })] }), showFindReplace && (jsxs("div", { style: {
1750
+ backgroundColor: '#f9fafb',
1751
+ border: '1px solid #ccc',
1752
+ borderTop: 'none',
1753
+ borderRadius: '0 0 4px 4px',
1754
+ padding: '16px',
1755
+ display: 'flex',
1756
+ alignItems: 'flex-start',
1757
+ gap: '12px',
1758
+ boxShadow: '0 2px 4px rgba(0, 0, 0, 0.05)',
1759
+ }, children: [jsxs("div", { style: { flex: '1', minWidth: '200px' }, children: [jsxs("div", { style: { position: 'relative' }, children: [jsx("input", { type: "text", value: searchQuery, onChange: function (e) { return onSearchQueryChange === null || onSearchQueryChange === void 0 ? void 0 : onSearchQueryChange(e.target.value); }, placeholder: "Find...", autoFocus: true, style: {
1760
+ width: '100%',
1761
+ padding: '8px 10px 8px 32px',
1762
+ border: searchQuery && totalMatches === 0 ? '1px solid #ef4444' : '1px solid #d1d5db',
1763
+ borderRadius: '6px',
1764
+ fontSize: '13px',
1765
+ outline: 'none',
1766
+ transition: 'all 0.2s',
1767
+ backgroundColor: 'white',
1768
+ boxSizing: 'border-box',
1769
+ }, onFocus: function (e) {
1770
+ if (!searchQuery || totalMatches > 0) {
1771
+ e.currentTarget.style.borderColor = '#3b82f6';
1772
+ }
1773
+ }, onBlur: function (e) {
1774
+ if (searchQuery && totalMatches === 0) {
1775
+ e.currentTarget.style.borderColor = '#ef4444';
1776
+ }
1777
+ else {
1778
+ e.currentTarget.style.borderColor = '#d1d5db';
1779
+ }
1780
+ } }), jsx(MagnifyingGlassIcon, { style: {
1781
+ width: '16px',
1782
+ height: '16px',
1783
+ position: 'absolute',
1784
+ left: '10px',
1785
+ top: '50%',
1786
+ transform: 'translateY(-50%)',
1787
+ color: '#9ca3af',
1788
+ pointerEvents: 'none',
1789
+ } })] }), searchQuery && (jsx("div", { style: {
1790
+ marginTop: '4px',
1791
+ fontSize: '11px',
1792
+ color: totalMatches === 0 ? '#ef4444' : '#6b7280',
1793
+ }, children: totalMatches === 0 ? 'No matches' : "".concat(currentMatchIndex + 1, " of ").concat(totalMatches) }))] }), searchQuery && (jsxs("div", { style: { display: 'flex', gap: '4px' }, children: [jsx("button", { onClick: handlePrevMatch, disabled: totalMatches === 0, title: "Previous match (Shift+Enter)", style: {
1794
+ padding: '8px',
1795
+ border: '1px solid #d1d5db',
1796
+ borderRadius: '6px',
1797
+ backgroundColor: totalMatches === 0 ? '#f3f4f6' : 'white',
1798
+ cursor: totalMatches === 0 ? 'not-allowed' : 'pointer',
1799
+ display: 'flex',
1800
+ alignItems: 'center',
1801
+ color: totalMatches === 0 ? '#d1d5db' : '#6b7280',
1802
+ transition: 'all 0.2s',
1803
+ }, onMouseEnter: function (e) {
1804
+ if (totalMatches > 0) {
1805
+ e.currentTarget.style.backgroundColor = '#f3f4f6';
1806
+ e.currentTarget.style.borderColor = '#9ca3af';
1807
+ }
1808
+ }, onMouseLeave: function (e) {
1809
+ if (totalMatches > 0) {
1810
+ e.currentTarget.style.backgroundColor = 'white';
1811
+ e.currentTarget.style.borderColor = '#d1d5db';
1812
+ }
1813
+ }, children: jsx(ChevronLeftIcon, { style: { width: '14px', height: '14px' } }) }), jsx("button", { onClick: handleNextMatch, disabled: totalMatches === 0, title: "Next match (Enter)", style: {
1814
+ padding: '8px',
1815
+ border: '1px solid #d1d5db',
1816
+ borderRadius: '6px',
1817
+ backgroundColor: totalMatches === 0 ? '#f3f4f6' : 'white',
1818
+ cursor: totalMatches === 0 ? 'not-allowed' : 'pointer',
1819
+ display: 'flex',
1820
+ alignItems: 'center',
1821
+ color: totalMatches === 0 ? '#d1d5db' : '#6b7280',
1822
+ transition: 'all 0.2s',
1823
+ }, onMouseEnter: function (e) {
1824
+ if (totalMatches > 0) {
1825
+ e.currentTarget.style.backgroundColor = '#f3f4f6';
1826
+ e.currentTarget.style.borderColor = '#9ca3af';
1827
+ }
1828
+ }, onMouseLeave: function (e) {
1829
+ if (totalMatches > 0) {
1830
+ e.currentTarget.style.backgroundColor = 'white';
1831
+ e.currentTarget.style.borderColor = '#d1d5db';
1832
+ }
1833
+ }, children: jsx(ChevronRightIcon, { style: { width: '14px', height: '14px' } }) })] })), jsx("div", { style: { flex: '1', minWidth: '200px' }, children: jsx("input", { type: "text", value: replaceText, onChange: function (e) { return setReplaceText(e.target.value); }, placeholder: "Replace...", style: {
1834
+ width: '100%',
1835
+ padding: '8px 10px',
1836
+ border: '1px solid #d1d5db',
1837
+ borderRadius: '6px',
1838
+ fontSize: '13px',
1839
+ outline: 'none',
1840
+ transition: 'all 0.2s',
1841
+ backgroundColor: 'white',
1842
+ boxSizing: 'border-box',
1843
+ }, onFocus: function (e) {
1844
+ e.currentTarget.style.borderColor = '#3b82f6';
1845
+ }, onBlur: function (e) {
1846
+ e.currentTarget.style.borderColor = '#d1d5db';
1847
+ } }) }), jsxs("div", { style: { display: 'flex', gap: '6px' }, children: [jsx("button", { onClick: handleReplace, disabled: searchMatches.length === 0, title: "Replace current match", style: {
1848
+ padding: '8px 12px',
1849
+ border: '1px solid #d1d5db',
1850
+ borderRadius: '6px',
1851
+ backgroundColor: searchMatches.length === 0 ? '#f3f4f6' : 'white',
1852
+ color: searchMatches.length === 0 ? '#9ca3af' : '#374151',
1853
+ cursor: searchMatches.length === 0 ? 'not-allowed' : 'pointer',
1854
+ fontSize: '13px',
1855
+ fontWeight: '500',
1856
+ whiteSpace: 'nowrap',
1857
+ transition: 'all 0.2s',
1858
+ }, onMouseEnter: function (e) {
1859
+ if (searchMatches.length > 0) {
1860
+ e.currentTarget.style.backgroundColor = '#f3f4f6';
1861
+ e.currentTarget.style.borderColor = '#9ca3af';
1862
+ }
1863
+ }, onMouseLeave: function (e) {
1864
+ if (searchMatches.length > 0) {
1865
+ e.currentTarget.style.backgroundColor = 'white';
1866
+ e.currentTarget.style.borderColor = '#d1d5db';
1867
+ }
1868
+ }, children: "Replace" }), jsx("button", { onClick: handleReplaceAll, disabled: searchMatches.length === 0, title: "Replace all matches", style: {
1869
+ padding: '8px 12px',
1870
+ border: 'none',
1871
+ borderRadius: '6px',
1872
+ backgroundColor: searchMatches.length === 0 ? '#cbd5e1' : '#3b82f6',
1873
+ color: 'white',
1874
+ cursor: searchMatches.length === 0 ? 'not-allowed' : 'pointer',
1875
+ fontSize: '13px',
1876
+ fontWeight: '500',
1877
+ whiteSpace: 'nowrap',
1878
+ transition: 'all 0.2s',
1879
+ }, onMouseEnter: function (e) {
1880
+ if (searchMatches.length > 0) {
1881
+ e.currentTarget.style.backgroundColor = '#2563eb';
1882
+ }
1883
+ }, onMouseLeave: function (e) {
1884
+ if (searchMatches.length > 0) {
1885
+ e.currentTarget.style.backgroundColor = '#3b82f6';
1886
+ }
1887
+ }, children: "Replace All" })] }), jsx("button", { onClick: function () { return setShowFindReplace(false); }, title: "Close (Esc)", style: {
1888
+ padding: '8px',
1889
+ border: '1px solid #d1d5db',
1890
+ borderRadius: '6px',
1891
+ backgroundColor: 'white',
1892
+ cursor: 'pointer',
1893
+ display: 'flex',
1894
+ alignItems: 'center',
1895
+ color: '#6b7280',
1896
+ transition: 'all 0.2s',
1897
+ }, onMouseEnter: function (e) {
1898
+ e.currentTarget.style.backgroundColor = '#fee2e2';
1899
+ e.currentTarget.style.borderColor = '#ef4444';
1900
+ e.currentTarget.style.color = '#dc2626';
1901
+ }, onMouseLeave: function (e) {
1902
+ e.currentTarget.style.backgroundColor = 'white';
1903
+ e.currentTarget.style.borderColor = '#d1d5db';
1904
+ e.currentTarget.style.color = '#6b7280';
1905
+ }, children: jsx(XMarkIcon, { style: { width: '16px', height: '16px' } }) })] }))] }));
1906
+ };
1907
+
1908
+ var ResizableImage = function (_a) {
1909
+ var element = _a.element, attributes = _a.attributes, children = _a.children;
1910
+ var editor = useSlateStatic();
1911
+ var selected = useSelected();
1912
+ var focused = useFocused();
1913
+ var _b = useState(false), isResizing = _b[0], setIsResizing = _b[1];
1914
+ var _c = useState({
1915
+ width: element.width || 0,
1916
+ height: element.height || 0,
1917
+ }), dimensions = _c[0], setDimensions = _c[1];
1918
+ var _d = useState(false), showActions = _d[0], setShowActions = _d[1];
1919
+ var imageRef = useRef(null);
1920
+ var startPos = useRef({ x: 0, y: 0, width: 0, height: 0 });
1921
+ var handleImageLoad = useCallback(function (e) {
1922
+ var img = e.currentTarget;
1923
+ if (!element.width && !element.height) {
1924
+ setDimensions({
1925
+ width: img.naturalWidth,
1926
+ height: img.naturalHeight,
1927
+ });
1928
+ }
1929
+ }, [element.width, element.height]);
1930
+ var handleMouseDown = useCallback(function (e, handle) {
1931
+ var _a, _b;
1932
+ e.preventDefault();
1933
+ e.stopPropagation();
1934
+ setIsResizing(true);
1935
+ var currentWidth = dimensions.width || ((_a = imageRef.current) === null || _a === void 0 ? void 0 : _a.offsetWidth) || 0;
1936
+ var currentHeight = dimensions.height || ((_b = imageRef.current) === null || _b === void 0 ? void 0 : _b.offsetHeight) || 0;
1937
+ startPos.current = {
1938
+ x: e.clientX,
1939
+ y: e.clientY,
1940
+ width: currentWidth,
1941
+ height: currentHeight,
1942
+ };
1943
+ var handleMouseMove = function (moveEvent) {
1944
+ var deltaX = moveEvent.clientX - startPos.current.x;
1945
+ var deltaY = moveEvent.clientY - startPos.current.y;
1946
+ var newWidth = startPos.current.width;
1947
+ var newHeight = startPos.current.height;
1948
+ switch (handle) {
1949
+ case 'se':
1950
+ newWidth = Math.max(100, startPos.current.width + deltaX);
1951
+ newHeight = Math.max(100, startPos.current.height + deltaY);
1952
+ break;
1953
+ case 'sw':
1954
+ newWidth = Math.max(100, startPos.current.width - deltaX);
1955
+ newHeight = Math.max(100, startPos.current.height + deltaY);
1956
+ break;
1957
+ case 'ne':
1958
+ newWidth = Math.max(100, startPos.current.width + deltaX);
1959
+ newHeight = Math.max(100, startPos.current.height - deltaY);
1960
+ break;
1961
+ case 'nw':
1962
+ newWidth = Math.max(100, startPos.current.width - deltaX);
1963
+ newHeight = Math.max(100, startPos.current.height - deltaY);
1964
+ break;
1965
+ case 'e':
1966
+ newWidth = Math.max(100, startPos.current.width + deltaX);
1967
+ newHeight = startPos.current.height;
1968
+ break;
1969
+ case 'w':
1970
+ newWidth = Math.max(100, startPos.current.width - deltaX);
1971
+ newHeight = startPos.current.height;
1972
+ break;
1973
+ case 'n':
1974
+ newWidth = startPos.current.width;
1975
+ newHeight = Math.max(100, startPos.current.height - deltaY);
1976
+ break;
1977
+ case 's':
1978
+ newWidth = startPos.current.width;
1979
+ newHeight = Math.max(100, startPos.current.height + deltaY);
1980
+ break;
1981
+ }
1982
+ setDimensions({ width: newWidth, height: newHeight });
1983
+ };
1984
+ var handleMouseUp = function () {
1985
+ setIsResizing(false);
1986
+ var path = ReactEditor.findPath(editor, element);
1987
+ Transforms.setNodes(editor, {
1988
+ width: dimensions.width,
1989
+ height: dimensions.height
1990
+ }, { at: path });
1991
+ document.removeEventListener('mousemove', handleMouseMove);
1992
+ document.removeEventListener('mouseup', handleMouseUp);
1993
+ };
1994
+ document.addEventListener('mousemove', handleMouseMove);
1995
+ document.addEventListener('mouseup', handleMouseUp);
1996
+ }, [dimensions, editor, element]);
1997
+ var handleRemoveImage = useCallback(function () {
1998
+ var path = ReactEditor.findPath(editor, element);
1999
+ Transforms.removeNodes(editor, { at: path });
2000
+ }, [editor, element]);
2001
+ var handleReplaceImage = useCallback(function () {
2002
+ if (window.__editiumImageReplaceHandler) {
2003
+ var path = ReactEditor.findPath(editor, element);
2004
+ window.__editiumImageReplaceHandler({
2005
+ url: element.url,
2006
+ alt: element.alt,
2007
+ width: element.width,
2008
+ height: element.height,
2009
+ align: element.align,
2010
+ path: path,
2011
+ });
2012
+ }
2013
+ }, [editor, element]);
2014
+ var handleAlignmentChange = useCallback(function (alignment) {
2015
+ var path = ReactEditor.findPath(editor, element);
2016
+ Transforms.setNodes(editor, { align: alignment }, { at: path });
2017
+ }, [editor, element]);
2018
+ var containerStyle = {
2019
+ display: 'flex',
2020
+ justifyContent: element.align === 'center' ? 'center' :
2021
+ element.align === 'right' ? 'flex-end' : 'flex-start',
2022
+ margin: '16px 0',
2023
+ position: 'relative',
2024
+ };
2025
+ var wrapperStyle = {
2026
+ position: 'relative',
2027
+ display: 'inline-block',
2028
+ maxWidth: '100%',
2029
+ cursor: isResizing ? 'nwse-resize' : 'default',
2030
+ };
2031
+ var imageStyle = {
2032
+ maxWidth: '100%',
2033
+ width: dimensions.width ? "".concat(dimensions.width, "px") : 'auto',
2034
+ height: dimensions.height ? "".concat(dimensions.height, "px") : 'auto',
2035
+ borderRadius: '4px',
2036
+ boxShadow: (selected && focused) || showActions
2037
+ ? '0 0 0 3px #3b82f6'
2038
+ : '0 1px 3px rgba(0, 0, 0, 0.1)',
2039
+ display: 'block',
2040
+ transition: showActions || (selected && focused) ? 'none' : 'box-shadow 0.2s ease',
2041
+ };
2042
+ var handleStyle = {
2043
+ position: 'absolute',
2044
+ width: '12px',
2045
+ height: '12px',
2046
+ backgroundColor: '#3b82f6',
2047
+ border: '2px solid #ffffff',
2048
+ borderRadius: '50%',
2049
+ opacity: showActions ? 1 : 0,
2050
+ transition: 'opacity 0.2s ease',
2051
+ pointerEvents: showActions ? 'auto' : 'none',
2052
+ zIndex: 10,
2053
+ };
2054
+ return (jsxs("div", __assign({}, attributes, { contentEditable: false, style: { userSelect: 'none' }, children: [jsx("div", { style: containerStyle, children: jsxs("div", { style: wrapperStyle, onMouseEnter: function () { return setShowActions(true); }, onMouseLeave: function () { return !isResizing && setShowActions(false); }, children: [jsx("img", { ref: imageRef, src: element.url, alt: element.alt || 'Image', style: imageStyle, onLoad: handleImageLoad, draggable: false }), ((selected && focused) || showActions) && (jsxs(Fragment, { children: [jsx("div", { style: __assign(__assign({}, handleStyle), { top: '-6px', left: '-6px', cursor: 'nw-resize' }), onMouseDown: function (e) { return handleMouseDown(e, 'nw'); }, title: "Resize" }), jsx("div", { style: __assign(__assign({}, handleStyle), { top: '-6px', right: '-6px', cursor: 'ne-resize' }), onMouseDown: function (e) { return handleMouseDown(e, 'ne'); }, title: "Resize" }), jsx("div", { style: __assign(__assign({}, handleStyle), { bottom: '-6px', left: '-6px', cursor: 'sw-resize' }), onMouseDown: function (e) { return handleMouseDown(e, 'sw'); }, title: "Resize" }), jsx("div", { style: __assign(__assign({}, handleStyle), { bottom: '-6px', right: '-6px', cursor: 'se-resize' }), onMouseDown: function (e) { return handleMouseDown(e, 'se'); }, title: "Resize" }), jsx("div", { style: __assign(__assign({}, handleStyle), { top: '-6px', left: '50%', transform: 'translateX(-50%)', cursor: 'n-resize' }), onMouseDown: function (e) { return handleMouseDown(e, 'n'); }, title: "Resize Height" }), jsx("div", { style: __assign(__assign({}, handleStyle), { bottom: '-6px', left: '50%', transform: 'translateX(-50%)', cursor: 's-resize' }), onMouseDown: function (e) { return handleMouseDown(e, 's'); }, title: "Resize Height" }), jsx("div", { style: __assign(__assign({}, handleStyle), { left: '-6px', top: '50%', transform: 'translateY(-50%)', cursor: 'w-resize' }), onMouseDown: function (e) { return handleMouseDown(e, 'w'); }, title: "Resize Width" }), jsx("div", { style: __assign(__assign({}, handleStyle), { right: '-6px', top: '50%', transform: 'translateY(-50%)', cursor: 'e-resize' }), onMouseDown: function (e) { return handleMouseDown(e, 'e'); }, title: "Resize Width" })] })), ((selected && focused) || showActions) && (jsxs("div", { style: {
2055
+ position: 'absolute',
2056
+ top: '8px',
2057
+ right: '8px',
2058
+ display: 'flex',
2059
+ flexDirection: 'column',
2060
+ gap: '8px',
2061
+ zIndex: 11,
2062
+ }, children: [jsxs("div", { style: {
2063
+ display: 'flex',
2064
+ gap: '4px',
2065
+ backgroundColor: '#ffffff',
2066
+ border: '1px solid #d1d5db',
2067
+ borderRadius: '4px',
2068
+ padding: '4px',
2069
+ boxShadow: '0 1px 2px rgba(0, 0, 0, 0.05)',
2070
+ }, children: [jsx("button", { onClick: function () { return handleAlignmentChange('left'); }, onMouseDown: function (e) { return e.preventDefault(); }, style: {
2071
+ padding: '4px 8px',
2072
+ backgroundColor: element.align === 'left' ? '#e0f2fe' : 'transparent',
2073
+ border: 'none',
2074
+ borderRadius: '2px',
2075
+ color: '#374151',
2076
+ fontSize: '12px',
2077
+ fontWeight: '500',
2078
+ cursor: 'pointer',
2079
+ transition: 'all 0.15s ease',
2080
+ }, onMouseEnter: function (e) {
2081
+ if (element.align !== 'left') {
2082
+ e.currentTarget.style.backgroundColor = '#f9fafb';
2083
+ }
2084
+ }, onMouseLeave: function (e) {
2085
+ if (element.align !== 'left') {
2086
+ e.currentTarget.style.backgroundColor = 'transparent';
2087
+ }
2088
+ }, title: "Align left", children: "\u2B05" }), jsx("button", { onClick: function () { return handleAlignmentChange('center'); }, onMouseDown: function (e) { return e.preventDefault(); }, style: {
2089
+ padding: '4px 8px',
2090
+ backgroundColor: element.align === 'center' ? '#e0f2fe' : 'transparent',
2091
+ border: 'none',
2092
+ borderRadius: '2px',
2093
+ color: '#374151',
2094
+ fontSize: '12px',
2095
+ fontWeight: '500',
2096
+ cursor: 'pointer',
2097
+ transition: 'all 0.15s ease',
2098
+ }, onMouseEnter: function (e) {
2099
+ if (element.align !== 'center') {
2100
+ e.currentTarget.style.backgroundColor = '#f9fafb';
2101
+ }
2102
+ }, onMouseLeave: function (e) {
2103
+ if (element.align !== 'center') {
2104
+ e.currentTarget.style.backgroundColor = 'transparent';
2105
+ }
2106
+ }, title: "Align center", children: "\u2194" }), jsx("button", { onClick: function () { return handleAlignmentChange('right'); }, onMouseDown: function (e) { return e.preventDefault(); }, style: {
2107
+ padding: '4px 8px',
2108
+ backgroundColor: element.align === 'right' ? '#e0f2fe' : 'transparent',
2109
+ border: 'none',
2110
+ borderRadius: '2px',
2111
+ color: '#374151',
2112
+ fontSize: '12px',
2113
+ fontWeight: '500',
2114
+ cursor: 'pointer',
2115
+ transition: 'all 0.15s ease',
2116
+ }, onMouseEnter: function (e) {
2117
+ if (element.align !== 'right') {
2118
+ e.currentTarget.style.backgroundColor = '#f9fafb';
2119
+ }
2120
+ }, onMouseLeave: function (e) {
2121
+ if (element.align !== 'right') {
2122
+ e.currentTarget.style.backgroundColor = 'transparent';
2123
+ }
2124
+ }, title: "Align right", children: "\u27A1" })] }), jsxs("div", { style: {
2125
+ display: 'flex',
2126
+ gap: '4px',
2127
+ }, children: [jsx("button", { onClick: handleReplaceImage, onMouseDown: function (e) { return e.preventDefault(); }, style: {
2128
+ padding: '6px 12px',
2129
+ backgroundColor: '#ffffff',
2130
+ border: '1px solid #d1d5db',
2131
+ borderRadius: '4px',
2132
+ color: '#374151',
2133
+ fontSize: '12px',
2134
+ fontWeight: '500',
2135
+ cursor: 'pointer',
2136
+ boxShadow: '0 1px 2px rgba(0, 0, 0, 0.05)',
2137
+ transition: 'all 0.15s ease',
2138
+ }, onMouseEnter: function (e) {
2139
+ e.currentTarget.style.backgroundColor = '#f9fafb';
2140
+ e.currentTarget.style.borderColor = '#9ca3af';
2141
+ }, onMouseLeave: function (e) {
2142
+ e.currentTarget.style.backgroundColor = '#ffffff';
2143
+ e.currentTarget.style.borderColor = '#d1d5db';
2144
+ }, title: "Replace image", children: "Replace" }), jsx("button", { onClick: handleRemoveImage, onMouseDown: function (e) { return e.preventDefault(); }, style: {
2145
+ padding: '6px 12px',
2146
+ backgroundColor: '#ffffff',
2147
+ border: '1px solid #d1d5db',
2148
+ borderRadius: '4px',
2149
+ color: '#dc2626',
2150
+ fontSize: '12px',
2151
+ fontWeight: '500',
2152
+ cursor: 'pointer',
2153
+ boxShadow: '0 1px 2px rgba(0, 0, 0, 0.05)',
2154
+ transition: 'all 0.15s ease',
2155
+ }, onMouseEnter: function (e) {
2156
+ e.currentTarget.style.backgroundColor = '#fef2f2';
2157
+ e.currentTarget.style.borderColor = '#fca5a5';
2158
+ }, onMouseLeave: function (e) {
2159
+ e.currentTarget.style.backgroundColor = '#ffffff';
2160
+ e.currentTarget.style.borderColor = '#d1d5db';
2161
+ }, title: "Remove image", children: "Remove" })] })] }))] }) }), children] })));
2162
+ };
2163
+
2164
+ var TableComponent = function (_a) {
2165
+ var element = _a.element, attributes = _a.attributes, children = _a.children;
2166
+ var editor = useSlateStatic();
2167
+ var selected = useSelected();
2168
+ var focused = useFocused();
2169
+ var _b = useState(false), showControls = _b[0], setShowControls = _b[1];
2170
+ var _c = useState(element.width || null), tableWidth = _c[0], setTableWidth = _c[1];
2171
+ var _d = useState(false), isResizing = _d[0], setIsResizing = _d[1];
2172
+ var tableRef = useRef(null);
2173
+ var handleAddRow = function () {
2174
+ addTableRow(editor);
2175
+ };
2176
+ var handleRemoveRow = function () {
2177
+ removeTableRow(editor);
2178
+ };
2179
+ var handleAddColumn = function () {
2180
+ addTableColumn(editor);
2181
+ };
2182
+ var handleRemoveColumn = function () {
2183
+ removeTableColumn(editor);
2184
+ };
2185
+ var handleDeleteTable = function () {
2186
+ Transforms.removeNodes(editor, {
2187
+ match: function (n) {
2188
+ return !Editor.isEditor(n) &&
2189
+ n.type === 'table';
2190
+ },
2191
+ });
2192
+ };
2193
+ var handleAlign = function (alignment) {
2194
+ setTableAlignment(editor, alignment);
2195
+ };
2196
+ var updateTableWidth = function (width) {
2197
+ setTableWidth(width);
2198
+ try {
2199
+ var path = ReactEditor.findPath(editor, element);
2200
+ Transforms.setNodes(editor, { width: width }, { at: path });
2201
+ }
2202
+ catch (error) {
2203
+ console.warn('Could not update table width:', error);
2204
+ }
2205
+ };
2206
+ return (jsx("div", { style: {
2207
+ position: 'relative',
2208
+ margin: '16px 0',
2209
+ display: 'flex',
2210
+ justifyContent: element.align === 'center' ? 'center' :
2211
+ element.align === 'right' ? 'flex-end' : 'flex-start',
2212
+ }, children: jsxs("div", __assign({}, attributes, { style: { position: 'relative', width: tableWidth ? "".concat(tableWidth, "px") : '100%', maxWidth: '100%' }, onMouseEnter: function () { return setShowControls(true); }, onMouseLeave: function () { return setShowControls(false); }, children: [jsx("table", { ref: tableRef, style: {
2213
+ borderCollapse: 'collapse',
2214
+ width: '100%',
2215
+ border: (selected && focused) || showControls ? '2px solid #3b82f6' : '1px solid #e5e7eb',
2216
+ transition: 'border 0.2s ease',
2217
+ }, children: jsx("tbody", { children: children }) }), ((selected && focused) || showControls) && (jsxs("div", { contentEditable: false, style: {
2218
+ position: 'absolute',
2219
+ top: '-40px',
2220
+ right: '0',
2221
+ display: 'flex',
2222
+ gap: '4px',
2223
+ backgroundColor: '#fff',
2224
+ padding: '4px',
2225
+ borderRadius: '6px',
2226
+ boxShadow: '0 2px 8px rgba(0, 0, 0, 0.15)',
2227
+ zIndex: 10,
2228
+ }, children: [jsxs("button", { onClick: handleAddRow, title: "Add Row", style: {
2229
+ display: 'flex',
2230
+ alignItems: 'center',
2231
+ gap: '4px',
2232
+ padding: '6px 10px',
2233
+ border: '1px solid #e5e7eb',
2234
+ borderRadius: '4px',
2235
+ backgroundColor: '#fff',
2236
+ cursor: 'pointer',
2237
+ fontSize: '13px',
2238
+ color: '#374151',
2239
+ }, onMouseOver: function (e) { return (e.currentTarget.style.backgroundColor = '#f3f4f6'); }, onMouseOut: function (e) { return (e.currentTarget.style.backgroundColor = '#fff'); }, children: [jsx(PlusIcon, { style: { width: '16px', height: '16px' } }), "Row"] }), jsxs("button", { onClick: handleRemoveRow, title: "Remove Row", style: {
2240
+ display: 'flex',
2241
+ alignItems: 'center',
2242
+ gap: '4px',
2243
+ padding: '6px 10px',
2244
+ border: '1px solid #e5e7eb',
2245
+ borderRadius: '4px',
2246
+ backgroundColor: '#fff',
2247
+ cursor: 'pointer',
2248
+ fontSize: '13px',
2249
+ color: '#374151',
2250
+ }, onMouseOver: function (e) { return (e.currentTarget.style.backgroundColor = '#f3f4f6'); }, onMouseOut: function (e) { return (e.currentTarget.style.backgroundColor = '#fff'); }, children: [jsx(MinusIcon, { style: { width: '16px', height: '16px' } }), "Row"] }), jsxs("button", { onClick: handleAddColumn, title: "Add Column", style: {
2251
+ display: 'flex',
2252
+ alignItems: 'center',
2253
+ gap: '4px',
2254
+ padding: '6px 10px',
2255
+ border: '1px solid #e5e7eb',
2256
+ borderRadius: '4px',
2257
+ backgroundColor: '#fff',
2258
+ cursor: 'pointer',
2259
+ fontSize: '13px',
2260
+ color: '#374151',
2261
+ }, onMouseOver: function (e) { return (e.currentTarget.style.backgroundColor = '#f3f4f6'); }, onMouseOut: function (e) { return (e.currentTarget.style.backgroundColor = '#fff'); }, children: [jsx(PlusIcon, { style: { width: '16px', height: '16px' } }), "Col"] }), jsxs("button", { onClick: handleRemoveColumn, title: "Remove Column", style: {
2262
+ display: 'flex',
2263
+ alignItems: 'center',
2264
+ gap: '4px',
2265
+ padding: '6px 10px',
2266
+ border: '1px solid #e5e7eb',
2267
+ borderRadius: '4px',
2268
+ backgroundColor: '#fff',
2269
+ cursor: 'pointer',
2270
+ fontSize: '13px',
2271
+ color: '#374151',
2272
+ }, onMouseOver: function (e) { return (e.currentTarget.style.backgroundColor = '#f3f4f6'); }, onMouseOut: function (e) { return (e.currentTarget.style.backgroundColor = '#fff'); }, children: [jsx(MinusIcon, { style: { width: '16px', height: '16px' } }), "Col"] }), jsx("div", { style: { width: '1px', height: '24px', backgroundColor: '#e5e7eb', margin: '0 4px' } }), jsx("button", { onClick: function () { return handleAlign('left'); }, title: "Align Left", style: {
2273
+ display: 'flex',
2274
+ alignItems: 'center',
2275
+ padding: '6px 8px',
2276
+ border: '1px solid #e5e7eb',
2277
+ borderRadius: '4px',
2278
+ backgroundColor: element.align === 'left' || !element.align ? '#e0e7ff' : '#fff',
2279
+ cursor: 'pointer',
2280
+ fontSize: '13px',
2281
+ color: '#374151',
2282
+ }, onMouseOver: function (e) {
2283
+ if (element.align !== 'left' && element.align)
2284
+ e.currentTarget.style.backgroundColor = '#f3f4f6';
2285
+ }, onMouseOut: function (e) {
2286
+ e.currentTarget.style.backgroundColor = element.align === 'left' || !element.align ? '#e0e7ff' : '#fff';
2287
+ }, children: jsx(Bars3BottomLeftIcon, { style: { width: '16px', height: '16px' } }) }), jsx("button", { onClick: function () { return handleAlign('center'); }, title: "Align Center", style: {
2288
+ display: 'flex',
2289
+ alignItems: 'center',
2290
+ padding: '6px 8px',
2291
+ border: '1px solid #e5e7eb',
2292
+ borderRadius: '4px',
2293
+ backgroundColor: element.align === 'center' ? '#e0e7ff' : '#fff',
2294
+ cursor: 'pointer',
2295
+ fontSize: '13px',
2296
+ color: '#374151',
2297
+ }, onMouseOver: function (e) {
2298
+ if (element.align !== 'center')
2299
+ e.currentTarget.style.backgroundColor = '#f3f4f6';
2300
+ }, onMouseOut: function (e) {
2301
+ e.currentTarget.style.backgroundColor = element.align === 'center' ? '#e0e7ff' : '#fff';
2302
+ }, children: jsx(Bars3Icon, { style: { width: '16px', height: '16px' } }) }), jsx("button", { onClick: function () { return handleAlign('right'); }, title: "Align Right", style: {
2303
+ display: 'flex',
2304
+ alignItems: 'center',
2305
+ padding: '6px 8px',
2306
+ border: '1px solid #e5e7eb',
2307
+ borderRadius: '4px',
2308
+ backgroundColor: element.align === 'right' ? '#e0e7ff' : '#fff',
2309
+ cursor: 'pointer',
2310
+ fontSize: '13px',
2311
+ color: '#374151',
2312
+ }, onMouseOver: function (e) {
2313
+ if (element.align !== 'right')
2314
+ e.currentTarget.style.backgroundColor = '#f3f4f6';
2315
+ }, onMouseOut: function (e) {
2316
+ e.currentTarget.style.backgroundColor = element.align === 'right' ? '#e0e7ff' : '#fff';
2317
+ }, children: jsx(Bars3BottomRightIcon, { style: { width: '16px', height: '16px' } }) }), jsx("div", { style: { width: '1px', height: '24px', backgroundColor: '#e5e7eb', margin: '0 4px' } }), jsxs("button", { onClick: handleDeleteTable, title: "Delete Table", style: {
2318
+ display: 'flex',
2319
+ alignItems: 'center',
2320
+ gap: '4px',
2321
+ padding: '6px 10px',
2322
+ border: '1px solid #e5e7eb',
2323
+ borderRadius: '4px',
2324
+ backgroundColor: '#fff',
2325
+ cursor: 'pointer',
2326
+ fontSize: '13px',
2327
+ color: '#dc2626',
2328
+ }, onMouseOver: function (e) {
2329
+ e.currentTarget.style.backgroundColor = '#fee2e2';
2330
+ }, onMouseOut: function (e) {
2331
+ e.currentTarget.style.backgroundColor = '#fff';
2332
+ }, children: [jsx(TrashIcon, { style: { width: '16px', height: '16px' } }), "Delete"] })] })), ((selected && focused) || showControls) && (jsx("div", { contentEditable: false, onMouseDown: function (e) {
2333
+ var _a;
2334
+ e.preventDefault();
2335
+ e.stopPropagation();
2336
+ setIsResizing(true);
2337
+ var startX = e.clientX;
2338
+ var startWidth = ((_a = tableRef.current) === null || _a === void 0 ? void 0 : _a.offsetWidth) || 0;
2339
+ var finalWidth = startWidth;
2340
+ var handleMouseMove = function (moveEvent) {
2341
+ var diff = moveEvent.clientX - startX;
2342
+ var newWidth = Math.max(200, startWidth + diff);
2343
+ finalWidth = newWidth;
2344
+ setTableWidth(newWidth);
2345
+ };
2346
+ var handleMouseUp = function () {
2347
+ setIsResizing(false);
2348
+ updateTableWidth(finalWidth);
2349
+ document.removeEventListener('mousemove', handleMouseMove);
2350
+ document.removeEventListener('mouseup', handleMouseUp);
2351
+ };
2352
+ document.addEventListener('mousemove', handleMouseMove);
2353
+ document.addEventListener('mouseup', handleMouseUp);
2354
+ }, style: {
2355
+ position: 'absolute',
2356
+ right: '-4px',
2357
+ top: '0',
2358
+ bottom: '0',
2359
+ width: '8px',
2360
+ cursor: 'col-resize',
2361
+ backgroundColor: isResizing ? '#3b82f6' : 'transparent',
2362
+ transition: 'background-color 0.2s',
2363
+ zIndex: 5,
2364
+ }, onMouseEnter: function (e) {
2365
+ if (!isResizing)
2366
+ e.currentTarget.style.backgroundColor = '#3b82f680';
2367
+ }, onMouseLeave: function (e) {
2368
+ if (!isResizing)
2369
+ e.currentTarget.style.backgroundColor = 'transparent';
2370
+ } }))] })) }));
2371
+ };
2372
+ var TableRowComponent = function (_a) {
2373
+ var attributes = _a.attributes, children = _a.children;
2374
+ return jsx("tr", __assign({}, attributes, { children: children }));
2375
+ };
2376
+ var TableCellComponent = function (_a) {
2377
+ var element = _a.element, attributes = _a.attributes, children = _a.children;
2378
+ var editor = useSlateStatic();
2379
+ var selected = useSelected();
2380
+ var focused = useFocused();
2381
+ var _b = useState(false), showAlignMenu = _b[0], setShowAlignMenu = _b[1];
2382
+ var menuRef = useRef(null);
2383
+ useEffect(function () {
2384
+ var handleClickOutside = function (event) {
2385
+ if (menuRef.current && !menuRef.current.contains(event.target)) {
2386
+ setShowAlignMenu(false);
2387
+ }
2388
+ };
2389
+ if (showAlignMenu) {
2390
+ document.addEventListener('mousedown', handleClickOutside);
2391
+ return function () { return document.removeEventListener('mousedown', handleClickOutside); };
2392
+ }
2393
+ }, [showAlignMenu]);
2394
+ var handleCellAlign = function (alignment) {
2395
+ var path = ReactEditor.findPath(editor, element);
2396
+ Transforms.setNodes(editor, { align: alignment }, { at: path });
2397
+ setShowAlignMenu(false);
2398
+ };
2399
+ return (jsxs("td", __assign({}, attributes, { style: {
2400
+ border: '1px solid #e5e7eb',
2401
+ padding: '8px 12px',
2402
+ minWidth: '100px',
2403
+ position: 'relative',
2404
+ textAlign: element.align || 'left',
2405
+ }, children: [selected && focused && (jsxs("div", { ref: menuRef, contentEditable: false, style: {
2406
+ position: 'absolute',
2407
+ top: '4px',
2408
+ right: '4px',
2409
+ zIndex: 10,
2410
+ }, children: [jsx("button", { onClick: function () { return setShowAlignMenu(!showAlignMenu); }, style: {
2411
+ padding: '2px 6px',
2412
+ border: '1px solid #e5e7eb',
2413
+ borderRadius: '3px',
2414
+ backgroundColor: '#fff',
2415
+ cursor: 'pointer',
2416
+ fontSize: '11px',
2417
+ color: '#6b7280',
2418
+ display: 'flex',
2419
+ alignItems: 'center',
2420
+ gap: '4px',
2421
+ }, onMouseOver: function (e) { return (e.currentTarget.style.backgroundColor = '#f3f4f6'); }, onMouseOut: function (e) { return (e.currentTarget.style.backgroundColor = '#fff'); }, title: "Align cell content", children: jsx(Bars3BottomLeftIcon, { style: { width: '12px', height: '12px' } }) }), showAlignMenu && (jsxs("div", { style: {
2422
+ position: 'absolute',
2423
+ top: '100%',
2424
+ right: '0',
2425
+ marginTop: '4px',
2426
+ backgroundColor: '#fff',
2427
+ border: '1px solid #e5e7eb',
2428
+ borderRadius: '6px',
2429
+ boxShadow: '0 4px 6px -1px rgba(0, 0, 0, 0.1)',
2430
+ padding: '4px',
2431
+ display: 'flex',
2432
+ gap: '2px',
2433
+ minWidth: '120px',
2434
+ }, children: [jsx("button", { onClick: function () { return handleCellAlign('left'); }, style: {
2435
+ padding: '4px 8px',
2436
+ border: 'none',
2437
+ borderRadius: '3px',
2438
+ backgroundColor: element.align === 'left' || !element.align ? '#e0e7ff' : 'transparent',
2439
+ cursor: 'pointer',
2440
+ display: 'flex',
2441
+ alignItems: 'center',
2442
+ justifyContent: 'center',
2443
+ }, onMouseOver: function (e) {
2444
+ if (element.align !== 'left' && element.align)
2445
+ e.currentTarget.style.backgroundColor = '#f3f4f6';
2446
+ }, onMouseOut: function (e) {
2447
+ e.currentTarget.style.backgroundColor = element.align === 'left' || !element.align ? '#e0e7ff' : 'transparent';
2448
+ }, title: "Align Left", children: jsx(Bars3BottomLeftIcon, { style: { width: '16px', height: '16px' } }) }), jsx("button", { onClick: function () { return handleCellAlign('center'); }, style: {
2449
+ padding: '4px 8px',
2450
+ border: 'none',
2451
+ borderRadius: '3px',
2452
+ backgroundColor: element.align === 'center' ? '#e0e7ff' : 'transparent',
2453
+ cursor: 'pointer',
2454
+ display: 'flex',
2455
+ alignItems: 'center',
2456
+ justifyContent: 'center',
2457
+ }, onMouseOver: function (e) {
2458
+ if (element.align !== 'center')
2459
+ e.currentTarget.style.backgroundColor = '#f3f4f6';
2460
+ }, onMouseOut: function (e) {
2461
+ e.currentTarget.style.backgroundColor = element.align === 'center' ? '#e0e7ff' : 'transparent';
2462
+ }, title: "Align Center", children: jsx(Bars3Icon, { style: { width: '16px', height: '16px' } }) }), jsx("button", { onClick: function () { return handleCellAlign('right'); }, style: {
2463
+ padding: '4px 8px',
2464
+ border: 'none',
2465
+ borderRadius: '3px',
2466
+ backgroundColor: element.align === 'right' ? '#e0e7ff' : 'transparent',
2467
+ cursor: 'pointer',
2468
+ display: 'flex',
2469
+ alignItems: 'center',
2470
+ justifyContent: 'center',
2471
+ }, onMouseOver: function (e) {
2472
+ if (element.align !== 'right')
2473
+ e.currentTarget.style.backgroundColor = '#f3f4f6';
2474
+ }, onMouseOut: function (e) {
2475
+ e.currentTarget.style.backgroundColor = element.align === 'right' ? '#e0e7ff' : 'transparent';
2476
+ }, title: "Align Right", children: jsx(Bars3BottomRightIcon, { style: { width: '16px', height: '16px' } }) })] }))] })), children] })));
2477
+ };
2478
+
2479
+ // All available toolbar items in a logical grouped order
2480
+ var ALL_TOOLBAR_ITEMS = [
2481
+ 'paragraph', 'heading-one', 'heading-two', 'heading-three', 'heading-four',
2482
+ 'heading-five', 'heading-six', 'heading-seven', 'heading-eight',
2483
+ 'separator',
2484
+ 'bold', 'italic', 'underline', 'strikethrough',
2485
+ 'separator',
2486
+ 'superscript', 'subscript', 'code',
2487
+ 'separator',
2488
+ 'left', 'center', 'right', 'justify',
2489
+ 'separator',
2490
+ 'text-color', 'bg-color',
2491
+ 'separator',
2492
+ 'blockquote', 'code-block',
2493
+ 'separator',
2494
+ 'bulleted-list', 'numbered-list', 'indent', 'outdent',
2495
+ 'separator',
2496
+ 'link', 'image', 'table', 'horizontal-rule', 'undo', 'redo',
2497
+ 'separator',
2498
+ 'find-replace', 'fullscreen', 'view-output'
2499
+ ];
2500
+
2501
+ var renderLeaf = function (_a) {
2502
+ var attributes = _a.attributes, children = _a.children, leaf = _a.leaf;
2503
+ var textLeaf = leaf;
2504
+ if (textLeaf.bold) {
2505
+ children = jsx("strong", { children: children });
2506
+ }
2507
+ if (textLeaf.italic) {
2508
+ children = jsx("em", { children: children });
2509
+ }
2510
+ if (textLeaf.underline) {
2511
+ children = jsx("u", { children: children });
2512
+ }
2513
+ if (textLeaf.strikethrough) {
2514
+ children = jsx("s", { children: children });
2515
+ }
2516
+ if (textLeaf.superscript) {
2517
+ children = jsx("sup", { children: children });
2518
+ }
2519
+ if (textLeaf.subscript) {
2520
+ children = jsx("sub", { children: children });
2521
+ }
2522
+ if (textLeaf.code) {
2523
+ children = jsx("code", { style: {
2524
+ backgroundColor: '#f4f4f4',
2525
+ padding: '2px 4px',
2526
+ borderRadius: '3px',
2527
+ fontFamily: 'monospace'
2528
+ }, children: children });
2529
+ }
2530
+ var style = {};
2531
+ if (textLeaf.color) {
2532
+ style.color = textLeaf.color;
2533
+ }
2534
+ if (textLeaf.backgroundColor) {
2535
+ style.backgroundColor = textLeaf.backgroundColor;
2536
+ }
2537
+ if (textLeaf.searchCurrent) {
2538
+ style.backgroundColor = '#ff9800';
2539
+ style.color = '#fff';
2540
+ }
2541
+ else if (textLeaf.search) {
2542
+ style.backgroundColor = '#ffeb3b';
2543
+ }
2544
+ return jsx("span", __assign({}, attributes, { style: Object.keys(style).length > 0 ? style : undefined, children: children }));
2545
+ };
2546
+ var parseInitialValue = function (initialValue) {
2547
+ if (!initialValue) {
2548
+ return defaultInitialValue;
2549
+ }
2550
+ if (typeof initialValue === 'string') {
2551
+ if (initialValue.trim() === '') {
2552
+ return defaultInitialValue;
2553
+ }
2554
+ return [
2555
+ {
2556
+ type: 'paragraph',
2557
+ children: [{ text: initialValue }],
2558
+ },
2559
+ ];
2560
+ }
2561
+ return initialValue.length > 0 ? initialValue : defaultInitialValue;
2562
+ };
2563
+ var withTables = function (editor) {
2564
+ var normalizeNode = editor.normalizeNode;
2565
+ editor.normalizeNode = function (entry) {
2566
+ var node = entry[0], path = entry[1];
2567
+ if (Element.isElement(node) && node.type === 'table') {
2568
+ for (var _i = 0, _a = Array.from(Editor.nodes(editor, { at: path })); _i < _a.length; _i++) {
2569
+ var _b = _a[_i], child = _b[0], childPath = _b[1];
2570
+ if (childPath.length === path.length + 1 && Element.isElement(child) && child.type !== 'table-row') {
2571
+ Transforms.removeNodes(editor, { at: childPath });
2572
+ return;
2573
+ }
2574
+ }
2575
+ }
2576
+ if (Element.isElement(node) && node.type === 'table-row') {
2577
+ for (var _c = 0, _d = Array.from(Editor.nodes(editor, { at: path })); _c < _d.length; _c++) {
2578
+ var _e = _d[_c], child = _e[0], childPath = _e[1];
2579
+ if (childPath.length === path.length + 1 && Element.isElement(child) && child.type !== 'table-cell') {
2580
+ Transforms.removeNodes(editor, { at: childPath });
2581
+ return;
2582
+ }
2583
+ }
2584
+ }
2585
+ normalizeNode(entry);
2586
+ };
2587
+ return editor;
2588
+ };
2589
+ var Editium = function (_a) {
2590
+ var initialValue = _a.initialValue, onChange = _a.onChange, _b = _a.toolbar, toolbar = _b === void 0 ? ['bold', 'italic', 'underline', 'heading-one', 'heading-two', 'bulleted-list', 'numbered-list', 'link'] : _b, _c = _a.placeholder, placeholder = _c === void 0 ? 'Start typing...' : _c, _d = _a.className, className = _d === void 0 ? '' : _d, _e = _a.style, style = _e === void 0 ? {} : _e, _f = _a.readOnly, readOnly = _f === void 0 ? false : _f, onImageUpload = _a.onImageUpload, externalSearchQuery = _a.searchQuery, externalSearchMatches = _a.searchMatches, externalCurrentMatchIndex = _a.currentMatchIndex, _g = _a.showWordCount, showWordCount = _g === void 0 ? true : _g, _h = _a.height, height = _h === void 0 ? '200px' : _h, _j = _a.minHeight, minHeight = _j === void 0 ? '150px' : _j, _k = _a.maxHeight, maxHeight = _k === void 0 ? '250px' : _k;
2591
+ var toolbarItems = toolbar === 'all' ? ALL_TOOLBAR_ITEMS : toolbar;
2592
+ var editor = useMemo(function () { return withTables(withHistory(withReact(createEditor()))); }, []);
2593
+ var _l = useState(function () { return parseInitialValue(initialValue); }), value = _l[0], setValue = _l[1];
2594
+ var _m = useState(null), showOutputModal = _m[0], setShowOutputModal = _m[1];
2595
+ var _o = useState(false), copySuccess = _o[0], setCopySuccess = _o[1];
2596
+ var _p = useState(false), showLinkPopup = _p[0], setShowLinkPopup = _p[1];
2597
+ var _q = useState({ x: 0, y: 0 }), linkPopupPosition = _q[0], setLinkPopupPosition = _q[1];
2598
+ var _r = useState(null), selectedLink = _r[0], setSelectedLink = _r[1];
2599
+ var _s = useState(false), isFullscreen = _s[0], setIsFullscreen = _s[1];
2600
+ var _t = useState(''), internalSearchQuery = _t[0], setInternalSearchQuery = _t[1];
2601
+ var _u = useState([]), internalSearchMatches = _u[0], setInternalSearchMatches = _u[1];
2602
+ var _v = useState(0), internalCurrentMatchIndex = _v[0], setInternalCurrentMatchIndex = _v[1];
2603
+ var searchQuery = externalSearchQuery !== undefined ? externalSearchQuery : internalSearchQuery;
2604
+ var searchMatches = externalSearchMatches !== undefined ? externalSearchMatches : internalSearchMatches;
2605
+ var currentMatchIndex = externalCurrentMatchIndex !== undefined ? externalCurrentMatchIndex : internalCurrentMatchIndex;
2606
+ useEffect(function () {
2607
+ window.__editiumProps = { onImageUpload: onImageUpload };
2608
+ return function () {
2609
+ delete window.__editiumProps;
2610
+ };
2611
+ }, [onImageUpload]);
2612
+ var _w = useState(null), selectedLinkPath = _w[0], setSelectedLinkPath = _w[1];
2613
+ var handleFullscreenToggle = useCallback(function () {
2614
+ setIsFullscreen(!isFullscreen);
2615
+ }, [isFullscreen]);
2616
+ useEffect(function () {
2617
+ var handleKeyDown = function (event) {
2618
+ if (event.key === 'F11') {
2619
+ event.preventDefault();
2620
+ setIsFullscreen(!isFullscreen);
2621
+ }
2622
+ if (event.key === 'Escape' && isFullscreen) {
2623
+ event.preventDefault();
2624
+ setIsFullscreen(false);
2625
+ }
2626
+ };
2627
+ window.addEventListener('keydown', handleKeyDown);
2628
+ return function () { return window.removeEventListener('keydown', handleKeyDown); };
2629
+ }, [isFullscreen]);
2630
+ useEffect(function () {
2631
+ if (isFullscreen) {
2632
+ var originalOverflow_1 = document.body.style.overflow;
2633
+ document.body.style.overflow = 'hidden';
2634
+ return function () {
2635
+ document.body.style.overflow = originalOverflow_1;
2636
+ };
2637
+ }
2638
+ }, [isFullscreen]);
2639
+ // Handle keyboard shortcuts
2640
+ var handleKeyDown = useCallback(function (event) {
2641
+ if (event.key === 'Delete' || event.key === 'Backspace') {
2642
+ var selection = editor.selection;
2643
+ if (selection) {
2644
+ var imageNode = Array.from(Editor.nodes(editor, {
2645
+ at: selection,
2646
+ match: function (n) {
2647
+ return !Editor.isEditor(n) &&
2648
+ Element.isElement(n) &&
2649
+ n.type === 'image';
2650
+ },
2651
+ }))[0];
2652
+ if (imageNode) {
2653
+ event.preventDefault();
2654
+ var imagePath = imageNode[1];
2655
+ Transforms.removeNodes(editor, { at: imagePath });
2656
+ return;
2657
+ }
2658
+ if (event.key === 'Delete' && Range.isCollapsed(selection)) {
2659
+ try {
2660
+ var after = Editor.after(editor, selection);
2661
+ if (after) {
2662
+ var nextNode = Array.from(Editor.nodes(editor, {
2663
+ at: after,
2664
+ match: function (n) {
2665
+ return !Editor.isEditor(n) &&
2666
+ Element.isElement(n) &&
2667
+ n.type === 'image';
2668
+ },
2669
+ }))[0];
2670
+ if (nextNode) {
2671
+ event.preventDefault();
2672
+ var nextPath = nextNode[1];
2673
+ Transforms.removeNodes(editor, { at: nextPath });
2674
+ return;
2675
+ }
2676
+ }
2677
+ }
2678
+ catch (e) {
2679
+ // Ignore errors if we can't find next node
2680
+ }
2681
+ }
2682
+ }
2683
+ }
2684
+ if (!event.ctrlKey && !event.metaKey) {
2685
+ return;
2686
+ }
2687
+ switch (event.key) {
2688
+ case 'b':
2689
+ event.preventDefault();
2690
+ toggleMark(editor, 'bold');
2691
+ break;
2692
+ case 'i':
2693
+ event.preventDefault();
2694
+ toggleMark(editor, 'italic');
2695
+ break;
2696
+ case 'u':
2697
+ event.preventDefault();
2698
+ toggleMark(editor, 'underline');
2699
+ break;
2700
+ case '`':
2701
+ event.preventDefault();
2702
+ toggleMark(editor, 'code');
2703
+ break;
2704
+ case 'd':
2705
+ event.preventDefault();
2706
+ toggleMark(editor, 'strikethrough');
2707
+ break;
2708
+ case 'z':
2709
+ if (event.shiftKey) {
2710
+ event.preventDefault();
2711
+ HistoryEditor.redo(editor);
2712
+ }
2713
+ else {
2714
+ event.preventDefault();
2715
+ HistoryEditor.undo(editor);
2716
+ }
2717
+ break;
2718
+ case 'y':
2719
+ event.preventDefault();
2720
+ HistoryEditor.redo(editor);
2721
+ break;
2722
+ }
2723
+ }, [editor]);
2724
+ var handleChange = useCallback(function (newValue) {
2725
+ setValue(newValue);
2726
+ if (onChange) {
2727
+ var htmlValue = serializeToHtml(newValue);
2728
+ onChange(htmlValue, newValue);
2729
+ }
2730
+ }, [onChange]);
2731
+ var textContent = useMemo(function () { return getTextContent(editor.children); }, [editor.children]);
2732
+ var wordCount = useMemo(function () { return countWords(textContent); }, [textContent]);
2733
+ var charCount = useMemo(function () { return countCharacters(textContent); }, [textContent]);
2734
+ var charCountNoSpaces = useMemo(function () { return countCharactersNoSpaces(textContent); }, [textContent]);
2735
+ useEffect(function () {
2736
+ if (initialValue !== undefined) {
2737
+ var parsedValue = parseInitialValue(initialValue);
2738
+ setValue(parsedValue);
2739
+ }
2740
+ }, [initialValue]);
2741
+ var handleCopy = useCallback(function () {
2742
+ var currentValue = editor.children;
2743
+ var textToCopy = showOutputModal === 'html'
2744
+ ? serializeToHtml(currentValue)
2745
+ : JSON.stringify(currentValue, null, 2);
2746
+ navigator.clipboard.writeText(textToCopy).then(function () {
2747
+ setCopySuccess(true);
2748
+ setTimeout(function () { return setCopySuccess(false); }, 2000);
2749
+ });
2750
+ }, [showOutputModal, editor]);
2751
+ var handleLinkClick = useCallback(function (event, linkElement) {
2752
+ event.preventDefault();
2753
+ var linkEntry = Array.from(Editor.nodes(editor, {
2754
+ match: function (n) { return n.type === 'link' && n.url === linkElement.url; },
2755
+ }))[0];
2756
+ if (linkEntry) {
2757
+ linkEntry[0]; var path = linkEntry[1];
2758
+ setSelectedLinkPath(path);
2759
+ }
2760
+ var rect = event.target.getBoundingClientRect();
2761
+ setLinkPopupPosition({
2762
+ x: rect.left + window.scrollX,
2763
+ y: rect.bottom + window.scrollY + 5
2764
+ });
2765
+ setSelectedLink(linkElement);
2766
+ setShowLinkPopup(true);
2767
+ }, [editor]);
2768
+ var decorate = useCallback(function (_a) {
2769
+ var node = _a[0], path = _a[1];
2770
+ var ranges = [];
2771
+ if (searchQuery && searchMatches.length > 0 && Text.isText(node)) {
2772
+ searchMatches.forEach(function (match, index) {
2773
+ if (JSON.stringify(match.path) === JSON.stringify(path)) {
2774
+ ranges.push({
2775
+ anchor: { path: path, offset: match.offset },
2776
+ focus: { path: path, offset: match.offset + match.text.length },
2777
+ search: true,
2778
+ searchCurrent: index === currentMatchIndex,
2779
+ });
2780
+ }
2781
+ });
2782
+ }
2783
+ return ranges;
2784
+ }, [searchQuery, searchMatches, currentMatchIndex]);
2785
+ var renderElementWithHandlers = useCallback(function (props) {
2786
+ var attributes = props.attributes, children = props.children, element = props.element;
2787
+ var style = { margin: '0', fontWeight: 'normal' };
2788
+ var alignStyle = element.align ? {
2789
+ textAlign: element.align
2790
+ } : {};
2791
+ var combinedStyle = __assign(__assign({}, style), alignStyle);
2792
+ switch (element.type) {
2793
+ case 'paragraph':
2794
+ return jsx("p", __assign({}, attributes, { style: combinedStyle, children: children }));
2795
+ case 'heading-one':
2796
+ return jsx("h1", __assign({}, attributes, { style: __assign(__assign({}, combinedStyle), { fontSize: '2em', margin: '0' }), children: children }));
2797
+ case 'heading-two':
2798
+ return jsx("h2", __assign({}, attributes, { style: __assign(__assign({}, combinedStyle), { fontSize: '1.5em', margin: '0' }), children: children }));
2799
+ case 'heading-three':
2800
+ return jsx("h3", __assign({}, attributes, { style: __assign(__assign({}, combinedStyle), { fontSize: '1.25em', margin: '0' }), children: children }));
2801
+ case 'heading-four':
2802
+ return jsx("h4", __assign({}, attributes, { style: __assign(__assign({}, combinedStyle), { fontSize: '1.1em', margin: '0' }), children: children }));
2803
+ case 'heading-five':
2804
+ return jsx("h5", __assign({}, attributes, { style: __assign(__assign({}, combinedStyle), { fontSize: '1em', margin: '0' }), children: children }));
2805
+ case 'heading-six':
2806
+ return jsx("h6", __assign({}, attributes, { style: __assign(__assign({}, combinedStyle), { fontSize: '0.9em', margin: '0' }), children: children }));
2807
+ case 'heading-seven':
2808
+ return jsx("h1", __assign({}, attributes, { style: __assign(__assign({}, combinedStyle), { fontSize: '0.85em', margin: '0' }), children: children }));
2809
+ case 'heading-eight':
2810
+ return jsx("h1", __assign({}, attributes, { style: __assign(__assign({}, combinedStyle), { fontSize: '0.8em', margin: '0' }), children: children }));
2811
+ case 'bulleted-list':
2812
+ return jsx("ul", __assign({}, attributes, { style: __assign(__assign({}, style), { margin: '0' }), children: children }));
2813
+ case 'numbered-list':
2814
+ return jsx("ol", __assign({}, attributes, { style: __assign(__assign({}, style), { margin: '0' }), children: children }));
2815
+ case 'list-item':
2816
+ return jsx("li", __assign({}, attributes, { children: children }));
2817
+ case 'blockquote':
2818
+ return (jsx("blockquote", __assign({}, attributes, { style: __assign(__assign({}, combinedStyle), { borderLeft: '4px solid #ddd', paddingLeft: '16px', marginLeft: '0', marginRight: '0', color: '#666', fontStyle: 'italic' }), children: children })));
2819
+ case 'code-block':
2820
+ return (jsx("pre", __assign({}, attributes, { style: {
2821
+ backgroundColor: '#f5f5f5',
2822
+ padding: '16px',
2823
+ borderRadius: '4px',
2824
+ overflow: 'auto',
2825
+ fontFamily: 'monospace',
2826
+ fontSize: '14px',
2827
+ lineHeight: '1.5',
2828
+ margin: '0'
2829
+ }, children: jsx("code", { children: children }) })));
2830
+ case 'horizontal-rule':
2831
+ return (jsxs("div", __assign({}, attributes, { contentEditable: false, style: { userSelect: 'none' }, children: [jsx("hr", { style: {
2832
+ border: 'none',
2833
+ borderTop: '2px solid #ddd',
2834
+ margin: '16px 0'
2835
+ } }), children] })));
2836
+ case 'image':
2837
+ var imageElement = element;
2838
+ return jsx(ResizableImage, { element: imageElement, attributes: attributes, children: children });
2839
+ case 'table':
2840
+ var tableElement = element;
2841
+ return jsx(TableComponent, { element: tableElement, attributes: attributes, children: children });
2842
+ case 'table-row':
2843
+ var tableRowElement = element;
2844
+ return jsx(TableRowComponent, { element: tableRowElement, attributes: attributes, children: children });
2845
+ case 'table-cell':
2846
+ var tableCellElement = element;
2847
+ return jsx(TableCellComponent, { element: tableCellElement, attributes: attributes, children: children });
2848
+ case 'link':
2849
+ var linkElement_1 = element;
2850
+ return (jsx("a", __assign({}, attributes, { href: linkElement_1.url, title: linkElement_1.title, onClick: function (e) { return handleLinkClick(e, linkElement_1); }, style: {
2851
+ color: '#0066cc',
2852
+ textDecoration: 'underline',
2853
+ cursor: 'pointer'
2854
+ }, children: children })));
2855
+ default:
2856
+ return jsx("p", __assign({}, attributes, { style: combinedStyle, children: children }));
2857
+ }
2858
+ }, [handleLinkClick]);
2859
+ var handleOpenLink = useCallback(function () {
2860
+ if (selectedLink) {
2861
+ window.open(selectedLink.url, selectedLink.target || '_self');
2862
+ setShowLinkPopup(false);
2863
+ }
2864
+ }, [selectedLink]);
2865
+ var handleRemoveLink = useCallback(function () {
2866
+ if (selectedLink) {
2867
+ var linkEntries = Array.from(Editor.nodes(editor, {
2868
+ match: function (n) {
2869
+ return !Editor.isEditor(n) &&
2870
+ Element.isElement(n) &&
2871
+ n.type === 'link' &&
2872
+ n.url === selectedLink.url;
2873
+ },
2874
+ }));
2875
+ if (linkEntries.length > 0) {
2876
+ var _a = linkEntries[0], linkNode = _a[0], linkPath = _a[1];
2877
+ var link = linkNode;
2878
+ if (linkPath.length === 1) {
2879
+ var textChildren = link.children;
2880
+ Transforms.removeNodes(editor, { at: linkPath });
2881
+ Transforms.insertNodes(editor, {
2882
+ type: 'paragraph',
2883
+ children: textChildren,
2884
+ }, {
2885
+ at: linkPath,
2886
+ });
2887
+ }
2888
+ else {
2889
+ Transforms.unwrapNodes(editor, {
2890
+ at: linkPath,
2891
+ });
2892
+ }
2893
+ }
2894
+ setShowLinkPopup(false);
2895
+ }
2896
+ }, [selectedLink, editor]);
2897
+ var handleEditLink = useCallback(function () {
2898
+ if (selectedLink && selectedLinkPath) {
2899
+ var linkText = Editor.string(editor, selectedLinkPath);
2900
+ if (window.__editiumLinkEditHandler) {
2901
+ window.__editiumLinkEditHandler({
2902
+ url: selectedLink.url,
2903
+ title: selectedLink.title,
2904
+ target: selectedLink.target,
2905
+ text: linkText,
2906
+ path: selectedLinkPath
2907
+ });
2908
+ }
2909
+ }
2910
+ setShowLinkPopup(false);
2911
+ }, [selectedLink, selectedLinkPath, editor]);
2912
+ var formatHtml = useCallback(function (html) {
2913
+ var formatted = '';
2914
+ var indent = 0;
2915
+ var tab = ' ';
2916
+ html.split(/(<[^>]+>)/g).forEach(function (part) {
2917
+ if (part.trim() === '')
2918
+ return;
2919
+ if (part.startsWith('</')) {
2920
+ indent--;
2921
+ formatted += tab.repeat(Math.max(0, indent)) + part + '\n';
2922
+ }
2923
+ else if (part.startsWith('<')) {
2924
+ formatted += tab.repeat(indent) + part + '\n';
2925
+ if (!part.includes('</') && !part.endsWith('/>')) {
2926
+ indent++;
2927
+ }
2928
+ }
2929
+ else {
2930
+ formatted += tab.repeat(indent) + part.trim() + '\n';
2931
+ }
2932
+ });
2933
+ return formatted.trim();
2934
+ }, []);
2935
+ var editorStyle = __assign({ border: '1px solid #ccc', borderTop: 'none', borderRadius: toolbar.length > 0 ? '0' : '4px 4px 0 0', borderBottom: 'none', padding: '16px', height: typeof height === 'number' ? "".concat(height, "px") : height, minHeight: typeof minHeight === 'number' ? "".concat(minHeight, "px") : minHeight, maxHeight: typeof maxHeight === 'number' ? "".concat(maxHeight, "px") : maxHeight, fontFamily: '-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif', fontSize: '14px', lineHeight: '1.6', outline: 'none', backgroundColor: '#fff', position: 'relative', overflow: 'auto' }, style);
2936
+ var containerStyle = isFullscreen ? {
2937
+ position: 'fixed',
2938
+ top: 0,
2939
+ left: 0,
2940
+ right: 0,
2941
+ bottom: 0,
2942
+ zIndex: 9999,
2943
+ backgroundColor: '#fff',
2944
+ display: 'flex',
2945
+ flexDirection: 'column',
2946
+ overflow: 'hidden',
2947
+ } : {};
2948
+ var editableStyle = isFullscreen ? __assign(__assign({}, editorStyle), { flex: 1, overflow: 'auto', border: 'none', borderRadius: 0,
2949
+ // Remove height constraints in fullscreen mode
2950
+ height: 'auto', minHeight: 'auto', maxHeight: 'none' }) : editorStyle;
2951
+ return (jsxs(Fragment, { children: [jsx("style", { children: "\n [data-slate-editor] {\n position: relative;\n min-height: inherit;\n height: 100%;\n }\n \n /* Custom scrollbar styling for better UX */\n [data-slate-editor]::-webkit-scrollbar {\n width: 8px;\n height: 8px;\n }\n \n [data-slate-editor]::-webkit-scrollbar-track {\n background: #f1f1f1;\n border-radius: 4px;\n }\n \n [data-slate-editor]::-webkit-scrollbar-thumb {\n background: #c1c1c1;\n border-radius: 4px;\n }\n \n [data-slate-editor]::-webkit-scrollbar-thumb:hover {\n background: #a8a8a8;\n }\n \n [data-slate-editor] [data-slate-placeholder] {\n opacity: 0.333;\n pointer-events: none;\n user-select: none;\n display: inline-block !important;\n width: 100%;\n max-width: 100%;\n white-space: nowrap;\n margin: 0 !important;\n vertical-align: text-top;\n }\n \n [data-slate-editor] p,\n [data-slate-editor] h1,\n [data-slate-editor] h2,\n [data-slate-editor] h3,\n [data-slate-editor] h4,\n [data-slate-editor] h5,\n [data-slate-editor] h6 {\n position: relative;\n }\n \n [data-slate-editor] [contenteditable=\"true\"] {\n outline: none;\n position: relative;\n z-index: 1;\n }\n \n [data-slate-editor] > * {\n margin: 0 !important;\n line-height: 1.6;\n }\n \n [data-slate-editor] p {\n margin: 0 !important;\n line-height: 1.6;\n }\n \n [data-slate-editor] h1,\n [data-slate-editor] h2,\n [data-slate-editor] h3,\n [data-slate-editor] h4,\n [data-slate-editor] h5,\n [data-slate-editor] h6 {\n margin: 0 !important;\n line-height: 1.6;\n }\n \n [data-slate-editor] ul,\n [data-slate-editor] ol {\n margin: 0 !important;\n padding-left: 24px;\n }\n " }), jsxs("div", { className: className, style: containerStyle, children: [showLinkPopup && (jsx("div", { style: {
2952
+ position: 'fixed',
2953
+ top: 0,
2954
+ left: 0,
2955
+ right: 0,
2956
+ bottom: 0,
2957
+ zIndex: 9998,
2958
+ }, onClick: function () { return setShowLinkPopup(false); }, children: jsxs("div", { style: {
2959
+ position: 'absolute',
2960
+ top: "".concat(linkPopupPosition.y, "px"),
2961
+ left: "".concat(linkPopupPosition.x, "px"),
2962
+ backgroundColor: '#ffffff',
2963
+ border: '1px solid #d1d5db',
2964
+ borderRadius: '8px',
2965
+ boxShadow: '0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05)',
2966
+ minWidth: '200px',
2967
+ overflow: 'hidden',
2968
+ zIndex: 9999,
2969
+ }, onClick: function (e) { return e.stopPropagation(); }, children: [selectedLink && (jsxs("div", { style: { padding: '8px 12px', borderBottom: '1px solid #e5e7eb', backgroundColor: '#f9fafb' }, children: [jsx("div", { style: { fontSize: '12px', color: '#6b7280', marginBottom: '4px' }, children: "Link URL:" }), jsx("div", { style: {
2970
+ fontSize: '13px',
2971
+ color: '#111827',
2972
+ wordBreak: 'break-all',
2973
+ fontFamily: 'monospace'
2974
+ }, children: selectedLink.url })] })), jsxs("button", { onClick: handleOpenLink, style: {
2975
+ width: '100%',
2976
+ padding: '12px 16px',
2977
+ border: 'none',
2978
+ backgroundColor: 'transparent',
2979
+ color: '#374151',
2980
+ fontSize: '14px',
2981
+ textAlign: 'left',
2982
+ cursor: 'pointer',
2983
+ display: 'flex',
2984
+ alignItems: 'center',
2985
+ gap: '10px',
2986
+ fontWeight: '500',
2987
+ }, onMouseEnter: function (e) { return e.currentTarget.style.backgroundColor = '#f3f4f6'; }, onMouseLeave: function (e) { return e.currentTarget.style.backgroundColor = 'transparent'; }, children: [jsx("svg", { style: { width: '16px', height: '16px' }, fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M10 6H6a2 2 0 00-2 2v10a2 2 0 002 2h10a2 2 0 002-2v-4M14 4h6m0 0v6m0-6L10 14" }) }), "Open Link"] }), jsxs("button", { onClick: handleEditLink, style: {
2988
+ width: '100%',
2989
+ padding: '12px 16px',
2990
+ border: 'none',
2991
+ backgroundColor: 'transparent',
2992
+ color: '#374151',
2993
+ fontSize: '14px',
2994
+ textAlign: 'left',
2995
+ cursor: 'pointer',
2996
+ display: 'flex',
2997
+ alignItems: 'center',
2998
+ gap: '10px',
2999
+ fontWeight: '500',
3000
+ }, onMouseEnter: function (e) { return e.currentTarget.style.backgroundColor = '#f3f4f6'; }, onMouseLeave: function (e) { return e.currentTarget.style.backgroundColor = 'transparent'; }, children: [jsx("svg", { style: { width: '16px', height: '16px' }, fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M11 5H6a2 2 0 00-2 2v11a2 2 0 002 2h11a2 2 0 002-2v-5m-1.414-9.414a2 2 0 112.828 2.828L11.828 15H9v-2.828l8.586-8.586z" }) }), "Edit Link"] }), jsxs("button", { onClick: handleRemoveLink, style: {
3001
+ width: '100%',
3002
+ padding: '12px 16px',
3003
+ border: 'none',
3004
+ borderTop: '1px solid #e5e7eb',
3005
+ backgroundColor: 'transparent',
3006
+ color: '#ef4444',
3007
+ fontSize: '14px',
3008
+ textAlign: 'left',
3009
+ cursor: 'pointer',
3010
+ display: 'flex',
3011
+ alignItems: 'center',
3012
+ gap: '10px',
3013
+ fontWeight: '500',
3014
+ }, onMouseEnter: function (e) { return e.currentTarget.style.backgroundColor = '#fef2f2'; }, onMouseLeave: function (e) { return e.currentTarget.style.backgroundColor = 'transparent'; }, children: [jsx("svg", { style: { width: '16px', height: '16px' }, fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M19 7l-.867 12.142A2 2 0 0116.138 21H7.862a2 2 0 01-1.995-1.858L5 7m5 4v6m4-6v6m1-10V4a1 1 0 00-1-1h-4a1 1 0 00-1 1v3M4 7h16" }) }), "Remove Link"] })] }) })), jsxs(Slate, { editor: editor, initialValue: value, onValueChange: handleChange, children: [toolbarItems.length > 0 && (jsx(Toolbar, { items: toolbarItems, onViewOutput: function (type) { return setShowOutputModal(type); }, onEditLink: function () { }, searchQuery: searchQuery, searchMatches: searchMatches, currentMatchIndex: currentMatchIndex, onSearchQueryChange: setInternalSearchQuery, onSearchMatchesChange: setInternalSearchMatches, onCurrentMatchIndexChange: setInternalCurrentMatchIndex, isFullscreen: isFullscreen, onFullscreenToggle: handleFullscreenToggle })), jsx(Editable, { renderElement: renderElementWithHandlers, renderLeaf: renderLeaf, decorate: decorate, placeholder: placeholder, onKeyDown: handleKeyDown, readOnly: readOnly, style: editableStyle })] }), jsxs("div", { style: {
3015
+ padding: '8px 12px',
3016
+ backgroundColor: '#f9fafb',
3017
+ borderTop: '1px solid #e5e7eb',
3018
+ borderLeft: isFullscreen ? 'none' : '1px solid #ccc',
3019
+ borderRight: isFullscreen ? 'none' : '1px solid #ccc',
3020
+ borderBottom: isFullscreen ? 'none' : '1px solid #ccc',
3021
+ borderRadius: isFullscreen ? '0' : '0 0 4px 4px',
3022
+ display: 'flex',
3023
+ justifyContent: showWordCount ? 'space-between' : 'flex-end',
3024
+ alignItems: 'center',
3025
+ gap: '20px',
3026
+ fontSize: '12px',
3027
+ color: '#6b7280',
3028
+ fontFamily: '-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif',
3029
+ }, children: [showWordCount && (jsxs("div", { style: { display: 'flex', gap: '20px' }, children: [jsxs("div", { style: { display: 'flex', alignItems: 'center', gap: '6px' }, children: [jsx("span", { style: { fontWeight: '500', color: '#374151' }, children: "Words:" }), jsx("span", { style: { fontWeight: '600', color: '#111827' }, children: wordCount.toLocaleString() })] }), jsxs("div", { style: { display: 'flex', alignItems: 'center', gap: '6px' }, children: [jsx("span", { style: { fontWeight: '500', color: '#374151' }, children: "Characters:" }), jsx("span", { style: { fontWeight: '600', color: '#111827' }, children: charCount.toLocaleString() })] }), jsxs("div", { style: { display: 'flex', alignItems: 'center', gap: '6px' }, children: [jsx("span", { style: { fontWeight: '500', color: '#374151' }, children: "Characters (no spaces):" }), jsx("span", { style: { fontWeight: '600', color: '#111827' }, children: charCountNoSpaces.toLocaleString() })] })] })), jsxs("div", { style: {
3030
+ display: 'flex',
3031
+ alignItems: 'center',
3032
+ gap: '6px',
3033
+ color: '#9ca3af',
3034
+ fontSize: '11px',
3035
+ }, children: [jsx("span", { children: "Built with" }), jsx("span", { style: {
3036
+ fontWeight: '600',
3037
+ color: '#3b82f6',
3038
+ letterSpacing: '0.5px',
3039
+ cursor: 'pointer',
3040
+ }, onClick: function (e) {
3041
+ e.preventDefault();
3042
+ window.open('https://www.npmjs.com/package/editium', '_blank');
3043
+ }, children: "Editium" })] })] }), showOutputModal && (jsx("div", { style: {
3044
+ position: 'fixed',
3045
+ top: 0,
3046
+ left: 0,
3047
+ right: 0,
3048
+ bottom: 0,
3049
+ backgroundColor: 'rgba(0, 0, 0, 0.5)',
3050
+ display: 'flex',
3051
+ alignItems: 'center',
3052
+ justifyContent: 'center',
3053
+ zIndex: 10000,
3054
+ }, onClick: function () {
3055
+ setShowOutputModal(null);
3056
+ setCopySuccess(false);
3057
+ }, children: jsxs("div", { style: {
3058
+ backgroundColor: '#ffffff',
3059
+ borderRadius: '8px',
3060
+ padding: '24px',
3061
+ maxWidth: '900px',
3062
+ maxHeight: '85vh',
3063
+ width: '90%',
3064
+ overflow: 'hidden',
3065
+ boxShadow: '0 20px 25px -5px rgba(0, 0, 0, 0.1), 0 10px 10px -5px rgba(0, 0, 0, 0.04)',
3066
+ display: 'flex',
3067
+ flexDirection: 'column',
3068
+ }, onClick: function (e) { return e.stopPropagation(); }, children: [jsxs("div", { style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: '16px' }, children: [jsx("h2", { style: { margin: 0, color: '#111827', fontSize: '24px', fontWeight: '600' }, children: showOutputModal === 'html' ? 'HTML Output' : showOutputModal === 'json' ? 'JSON Output' : 'Preview' }), jsxs("div", { style: { display: 'flex', gap: '8px', alignItems: 'center' }, children: [showOutputModal !== 'preview' && (jsx("button", { onClick: handleCopy, style: {
3069
+ backgroundColor: copySuccess ? '#10b981' : '#3b82f6',
3070
+ color: '#ffffff',
3071
+ border: 'none',
3072
+ borderRadius: '6px',
3073
+ padding: '8px 16px',
3074
+ fontSize: '14px',
3075
+ fontWeight: '500',
3076
+ cursor: 'pointer',
3077
+ transition: 'all 0.2s ease-in-out',
3078
+ display: 'flex',
3079
+ alignItems: 'center',
3080
+ gap: '6px',
3081
+ }, onMouseEnter: function (e) {
3082
+ if (!copySuccess) {
3083
+ e.currentTarget.style.backgroundColor = '#2563eb';
3084
+ }
3085
+ }, onMouseLeave: function (e) {
3086
+ if (!copySuccess) {
3087
+ e.currentTarget.style.backgroundColor = '#3b82f6';
3088
+ }
3089
+ }, title: "Copy to clipboard", children: copySuccess ? (jsxs(Fragment, { children: [jsx("svg", { style: { width: '16px', height: '16px' }, fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M5 13l4 4L19 7" }) }), "Copied!"] })) : (jsxs(Fragment, { children: [jsx("svg", { style: { width: '16px', height: '16px' }, fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M8 16H6a2 2 0 01-2-2V6a2 2 0 012-2h8a2 2 0 012 2v2m-6 12h8a2 2 0 002-2v-8a2 2 0 00-2-2h-8a2 2 0 00-2 2v8a2 2 0 002 2z" }) }), "Copy"] })) })), jsx("button", { onClick: function () {
3090
+ setShowOutputModal(null);
3091
+ setCopySuccess(false);
3092
+ }, style: {
3093
+ background: 'none',
3094
+ border: 'none',
3095
+ fontSize: '24px',
3096
+ cursor: 'pointer',
3097
+ color: '#6b7280',
3098
+ padding: '4px',
3099
+ lineHeight: 1,
3100
+ }, title: "Close", children: "\u00D7" })] })] }), jsx("div", { style: {
3101
+ flex: 1,
3102
+ overflow: 'auto',
3103
+ backgroundColor: showOutputModal === 'preview' ? '#ffffff' : '#1e293b',
3104
+ borderRadius: '6px',
3105
+ border: showOutputModal === 'preview' ? '1px solid #e5e7eb' : '1px solid #334155',
3106
+ padding: showOutputModal === 'preview' ? '20px' : '0',
3107
+ }, children: showOutputModal === 'preview' ? (jsx("div", { dangerouslySetInnerHTML: { __html: serializeToHtml(editor.children) }, style: {
3108
+ fontFamily: '-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif',
3109
+ fontSize: '16px',
3110
+ lineHeight: '1.6',
3111
+ color: '#111827',
3112
+ } })) : (jsx("pre", { style: {
3113
+ margin: 0,
3114
+ padding: '20px',
3115
+ fontSize: '13px',
3116
+ lineHeight: '1.6',
3117
+ fontFamily: 'Consolas, Monaco, "Courier New", monospace',
3118
+ color: '#e2e8f0',
3119
+ overflowX: 'auto',
3120
+ whiteSpace: 'pre-wrap',
3121
+ wordBreak: 'break-word',
3122
+ }, children: jsx("code", { children: showOutputModal === 'html'
3123
+ ? formatHtml(serializeToHtml(editor.children))
3124
+ : JSON.stringify(editor.children, null, 2) }) })) })] }) }))] })] }));
3125
+ };
3126
+
3127
+ export { ALL_TOOLBAR_ITEMS, Editium, ResizableImage, TableCellComponent, TableComponent, TableRowComponent, addTableColumn, addTableRow, defaultInitialValue, findAllMatches, insertLink, insertTable, isBlockActive, isInTable, isLinkActive, isMarkActive, navigateToMatch, removeTableColumn, removeTableRow, replaceAllMatches, replaceMatch, serializeToHtml, setTableAlignment, toggleBlock, toggleMark };
3128
+ //# sourceMappingURL=index.esm.js.map