tiptap-markdown-react 0.6.2 → 0.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -1,16 +1,18 @@
1
1
  "use client";
2
2
  import { Markdown } from "@tiptap/markdown";
3
- import { jsx, jsxs, Fragment } from "react/jsx-runtime";
3
+ import { jsx, jsxs, Fragment as Fragment$1 } from "react/jsx-runtime";
4
4
  import CodeBlockLowlight from "@tiptap/extension-code-block-lowlight";
5
5
  import Image from "@tiptap/extension-image";
6
6
  import { TableOfContents } from "@tiptap/extension-table-of-contents";
7
7
  import { NodeViewWrapper, ReactNodeViewRenderer, NodeViewContent, useEditor, EditorContent, useEditorState } from "@tiptap/react";
8
- import { forwardRef, useEffect, useImperativeHandle, useMemo, useState, useRef, useCallback, useContext, createContext } from "react";
9
- import { C as CitationRef, e as enrichMarkdownCitations, s as styles$4, b as baseExtensions, l as lowlight, m as makeTocGetId, p as pureCodeBlock, a as pureImage, R as ReportContent } from "./extractToc-CSawxIx-.js";
10
- import { c, d } from "./extractToc-CSawxIx-.js";
8
+ import { forwardRef, useEffect, useRef, useImperativeHandle, useMemo, useState, useCallback, useContext, createContext } from "react";
9
+ import { C as CitationRef, m as mergeCommentIntervals, a as mapCommentAnchors, e as enrichMarkdownCitations, s as styles$5, b as baseExtensions, c as CommentMark, l as lowlight, d as makeTocGetId, p as pureCodeBlock, f as pureImage, R as ReportContent } from "./extractToc-AUH9u6o-.js";
10
+ import { g, h, i } from "./extractToc-AUH9u6o-.js";
11
+ import { Slice, Fragment } from "@tiptap/pm/model";
11
12
  import { Extension } from "@tiptap/core";
12
- import { FileHandlePlugin } from "@tiptap/extension-file-handler";
13
13
  import { PluginKey, Plugin } from "@tiptap/pm/state";
14
+ import { DecorationSet, Decoration } from "@tiptap/pm/view";
15
+ import { FileHandlePlugin } from "@tiptap/extension-file-handler";
14
16
  import * as DropdownMenu from "@radix-ui/react-dropdown-menu";
15
17
  import * as Popover from "@radix-ui/react-popover";
16
18
  import { createPortal } from "react-dom";
@@ -70,6 +72,259 @@ function createCitationRef(options = {}) {
70
72
  renderCitation: options.renderCitation
71
73
  });
72
74
  }
75
+ const COMMENT_ACTIVE_META = "tmr:comment:active";
76
+ const COMMENT_CLICK_META = "tmr:comment:click";
77
+ const COMMENT_GUTTER_META = "tmr:comment:gutter";
78
+ const commentAnchorPluginKey = new PluginKey(
79
+ "tmrCommentAnchor"
80
+ );
81
+ function stripCommentAnchorMarks(slice, markType) {
82
+ const strip = (fragment) => {
83
+ const children = [];
84
+ fragment.forEach((child) => {
85
+ if (child.isText && child.marks.some((m) => m.type === markType)) {
86
+ children.push(
87
+ child.mark(child.marks.filter((m) => m.type !== markType))
88
+ );
89
+ } else if (child.content.size > 0) {
90
+ children.push(child.copy(strip(child.content)));
91
+ } else {
92
+ children.push(child);
93
+ }
94
+ });
95
+ return Fragment.fromArray(children);
96
+ };
97
+ return new Slice(strip(slice.content), slice.openStart, slice.openEnd);
98
+ }
99
+ function sliceHasCommentMarks(slice, markType) {
100
+ let found = false;
101
+ slice.content.descendants((node) => {
102
+ if (node.isText && node.marks.some((m) => m.type === markType)) {
103
+ found = true;
104
+ return false;
105
+ }
106
+ return true;
107
+ });
108
+ return found;
109
+ }
110
+ function blockBounds(doc) {
111
+ const bounds = [];
112
+ doc.forEach((child, offset) => {
113
+ bounds.push({ start: offset, end: offset + child.nodeSize });
114
+ });
115
+ return bounds;
116
+ }
117
+ function collectCommentRanges(doc) {
118
+ const byId = /* @__PURE__ */ new Map();
119
+ doc.descendants((node, pos) => {
120
+ if (!node.isText) return true;
121
+ for (const m of node.marks) {
122
+ if (m.type.name !== "commentAnchor") continue;
123
+ const ids = m.attrs.commentIds ?? [];
124
+ for (const id of ids) {
125
+ const arr = byId.get(id) ?? [];
126
+ arr.push({ from: pos, to: pos + node.nodeSize });
127
+ byId.set(id, arr);
128
+ }
129
+ }
130
+ return true;
131
+ });
132
+ return byId;
133
+ }
134
+ function rangesIntersectBlock(ranges, start, end) {
135
+ return ranges.some((r) => r.from < end && r.to > start);
136
+ }
137
+ function gutterDom(commentIds, view, blockPos) {
138
+ const el = document.createElement("span");
139
+ el.className = "tmr-comment-gutter";
140
+ el.setAttribute("data-comment-ids", commentIds.join(" "));
141
+ el.textContent = String(commentIds.length);
142
+ el.title = `${commentIds.length}`;
143
+ el.addEventListener("mousedown", (e) => {
144
+ e.preventDefault();
145
+ e.stopPropagation();
146
+ });
147
+ el.addEventListener("click", (e) => {
148
+ e.preventDefault();
149
+ e.stopPropagation();
150
+ view.dispatch(
151
+ view.state.tr.setMeta(COMMENT_ACTIVE_META, commentIds[0] ?? null).setMeta(COMMENT_GUTTER_META, {
152
+ commentIds,
153
+ pos: blockPos
154
+ })
155
+ );
156
+ });
157
+ return el;
158
+ }
159
+ function commentAnchorPlugin(options = {}) {
160
+ const showGutter = options.showGutter !== false;
161
+ return new Plugin({
162
+ key: commentAnchorPluginKey,
163
+ state: {
164
+ init: () => ({ activeCommentId: null }),
165
+ apply: (tr, value) => {
166
+ const active2 = tr.getMeta(COMMENT_ACTIVE_META);
167
+ return active2 !== void 0 ? { activeCommentId: active2 } : value;
168
+ }
169
+ },
170
+ props: {
171
+ decorations(state) {
172
+ var _a;
173
+ const byId = collectCommentRanges(state.doc);
174
+ if (byId.size === 0) return DecorationSet.empty;
175
+ const decos = [];
176
+ const bounds = blockBounds(state.doc);
177
+ if (showGutter) {
178
+ for (const b of bounds) {
179
+ const idsInBlock = [];
180
+ for (const [id, ranges] of byId) {
181
+ if (rangesIntersectBlock(ranges, b.start, b.end)) {
182
+ idsInBlock.push(id);
183
+ }
184
+ }
185
+ if (idsInBlock.length > 0) {
186
+ decos.push(
187
+ Decoration.widget(
188
+ b.start,
189
+ (view) => gutterDom(idsInBlock, view, b.start),
190
+ { side: -1, key: `tmr-gutter:${b.start}` }
191
+ )
192
+ );
193
+ }
194
+ }
195
+ }
196
+ const activeId = ((_a = commentAnchorPluginKey.getState(state)) == null ? void 0 : _a.activeCommentId) ?? null;
197
+ if (activeId) {
198
+ const ranges = byId.get(activeId) ?? [];
199
+ for (const r of ranges) {
200
+ decos.push(
201
+ Decoration.inline(r.from, r.to, { class: "tmr-comment-active" })
202
+ );
203
+ }
204
+ for (const b of bounds) {
205
+ if (rangesIntersectBlock(ranges, b.start, b.end)) {
206
+ decos.push(
207
+ Decoration.node(b.start, b.end, {
208
+ class: "tmr-comment-block-active"
209
+ })
210
+ );
211
+ }
212
+ }
213
+ }
214
+ return DecorationSet.create(state.doc, decos);
215
+ },
216
+ handleClick(view, pos, event) {
217
+ var _a;
218
+ const target = event.target;
219
+ const el = (_a = target == null ? void 0 : target.closest) == null ? void 0 : _a.call(
220
+ target,
221
+ "mark.tmr-comment[data-comment-ids]"
222
+ );
223
+ if (!el) return false;
224
+ const commentIds = (el.getAttribute("data-comment-ids") ?? "").split(" ").filter(Boolean);
225
+ if (commentIds.length === 0) return false;
226
+ view.dispatch(
227
+ view.state.tr.setMeta(COMMENT_ACTIVE_META, commentIds[0] ?? null).setMeta(COMMENT_CLICK_META, {
228
+ commentIds,
229
+ anchorEl: el,
230
+ pos
231
+ })
232
+ );
233
+ return true;
234
+ },
235
+ // 粘贴 / 拖拽 / 编辑器内拖动的 slice 统一走这里:剥离评论 mark,
236
+ // 防止复制粘贴产生幽灵高亮。正文内容不变,只是丢掉会话级元数据。
237
+ transformPasted(slice, view) {
238
+ const markType = view.state.schema.marks.commentAnchor;
239
+ if (!markType || !sliceHasCommentMarks(slice, markType)) return slice;
240
+ return stripCommentAnchorMarks(slice, markType);
241
+ }
242
+ }
243
+ });
244
+ }
245
+ function commentAnchorExtension(options = {}) {
246
+ return Extension.create({
247
+ name: "tmrCommentAnchor",
248
+ addProseMirrorPlugins() {
249
+ return [commentAnchorPlugin(options)];
250
+ }
251
+ });
252
+ }
253
+ function applyCommentAnchorsToEditor(editor, comments) {
254
+ if (!editor.isEditable) return;
255
+ const intervals = comments.length > 0 ? mergeCommentIntervals(
256
+ mapCommentAnchors(
257
+ editor.state.doc,
258
+ comments.map((c) => ({ commentId: c.commentId, segments: c.segments }))
259
+ ).map((r) => ({ commentId: r.commentId, ranges: r.ranges }))
260
+ ) : [];
261
+ const chain = editor.chain().clearCommentAnchors();
262
+ if (intervals.length > 0) chain.applyCommentAnchors(intervals);
263
+ chain.run();
264
+ }
265
+ function collectCommentIds(editor) {
266
+ const ids = [];
267
+ editor.state.doc.descendants((node) => {
268
+ if (!node.isText) return true;
269
+ for (const m of node.marks) {
270
+ if (m.type.name !== "commentAnchor") continue;
271
+ for (const id of m.attrs.commentIds ?? []) {
272
+ if (!ids.includes(id)) ids.push(id);
273
+ }
274
+ }
275
+ return true;
276
+ });
277
+ return ids;
278
+ }
279
+ function commentRangesById(editor, commentId) {
280
+ const ranges = [];
281
+ editor.state.doc.descendants((node, pos) => {
282
+ if (!node.isText) return true;
283
+ for (const m of node.marks) {
284
+ if (m.type.name !== "commentAnchor") continue;
285
+ const ids = m.attrs.commentIds ?? [];
286
+ if (ids.includes(commentId)) {
287
+ ranges.push({ from: pos, to: pos + node.nodeSize });
288
+ }
289
+ }
290
+ return true;
291
+ });
292
+ return ranges;
293
+ }
294
+ function setActive(editor, commentId) {
295
+ editor.view.dispatch(
296
+ editor.state.tr.setMeta(COMMENT_ACTIVE_META, commentId)
297
+ );
298
+ }
299
+ function getActive(editor) {
300
+ var _a;
301
+ return ((_a = commentAnchorPluginKey.getState(editor.state)) == null ? void 0 : _a.activeCommentId) ?? null;
302
+ }
303
+ function focusComment(editor, commentId) {
304
+ var _a;
305
+ const ranges = commentRangesById(editor, commentId);
306
+ if (ranges.length === 0) {
307
+ setActive(editor, null);
308
+ return false;
309
+ }
310
+ setActive(editor, commentId);
311
+ const markEl = editor.view.dom.querySelector(
312
+ `mark.tmr-comment[data-comment-ids~="${CSS.escape(commentId)}"]`
313
+ );
314
+ (_a = markEl == null ? void 0 : markEl.scrollIntoView) == null ? void 0 : _a.call(markEl, { block: "center", behavior: "smooth" });
315
+ editor.chain().setTextSelection(ranges[0].from).run();
316
+ return true;
317
+ }
318
+ function nextComment(editor, dir = "next") {
319
+ const ids = collectCommentIds(editor);
320
+ if (ids.length === 0) return null;
321
+ const active2 = getActive(editor);
322
+ const current = active2 ? ids.indexOf(active2) : -1;
323
+ const nextIdx = dir === "next" ? (current + 1) % ids.length : (current - 1 + ids.length) % ids.length;
324
+ const target = ids[nextIdx];
325
+ focusComment(editor, target);
326
+ return target;
327
+ }
73
328
  const MD_FILE_RE = /\.(md|markdown)$/i;
74
329
  const MD_MIME_TYPES = ["text/markdown", "text/x-markdown", ""];
75
330
  async function insertMarkdownFiles(editor, files, pos) {
@@ -343,21 +598,32 @@ const defaultCodeBlockLabels = {
343
598
  autoDetect: "Auto-detect",
344
599
  delete: "Delete code block"
345
600
  };
346
- const wrapper = "_wrapper_2dv2g_2";
347
- const header$1 = "_header_2dv2g_18";
348
- const langTrigger = "_langTrigger_2dv2g_28";
349
- const langChevron = "_langChevron_2dv2g_50";
350
- const langMenu = "_langMenu_2dv2g_56";
351
- const langItem = "_langItem_2dv2g_69";
352
- const langItemSelected = "_langItemSelected_2dv2g_88";
353
- const langItemCheck = "_langItemCheck_2dv2g_93";
354
- const deleteBtn = "_deleteBtn_2dv2g_101";
355
- const pre = "_pre_2dv2g_121";
356
- const styles$3 = {
601
+ const defaultCommentLabels = {
602
+ open: "Open",
603
+ resolved: "Resolved",
604
+ dismissed: "Dismissed",
605
+ outdated: "Outdated",
606
+ ambiguous: "Ambiguous",
607
+ partial: "Partially matched",
608
+ gutterTitle: "Comment"
609
+ };
610
+ const wrapper = "_wrapper_5i2vi_2";
611
+ const header$1 = "_header_5i2vi_18";
612
+ const langTrigger = "_langTrigger_5i2vi_28";
613
+ const langChevron = "_langChevron_5i2vi_50";
614
+ const langBadge = "_langBadge_5i2vi_56";
615
+ const langMenu = "_langMenu_5i2vi_71";
616
+ const langItem = "_langItem_5i2vi_84";
617
+ const langItemSelected = "_langItemSelected_5i2vi_103";
618
+ const langItemCheck = "_langItemCheck_5i2vi_108";
619
+ const deleteBtn = "_deleteBtn_5i2vi_116";
620
+ const pre = "_pre_5i2vi_136";
621
+ const styles$4 = {
357
622
  wrapper,
358
623
  header: header$1,
359
624
  langTrigger,
360
625
  langChevron,
626
+ langBadge,
361
627
  langMenu,
362
628
  langItem,
363
629
  langItemSelected,
@@ -389,7 +655,8 @@ function CodeBlockView({
389
655
  node,
390
656
  updateAttributes,
391
657
  deleteNode,
392
- extension
658
+ extension,
659
+ editor
393
660
  }) {
394
661
  var _a;
395
662
  const labels = {
@@ -399,25 +666,26 @@ function CodeBlockView({
399
666
  const language = node.attrs.language || "";
400
667
  const current = LANGUAGES.find((l) => l.value === language);
401
668
  const currentLabel = current ? current.value === "" ? labels.autoDetect : current.label : labels.autoDetect;
402
- return /* @__PURE__ */ jsxs(NodeViewWrapper, { className: styles$3.wrapper, children: [
403
- /* @__PURE__ */ jsxs("div", { className: styles$3.header, contentEditable: false, children: [
669
+ const editable = editor.isEditable;
670
+ return /* @__PURE__ */ jsxs(NodeViewWrapper, { className: styles$4.wrapper, children: [
671
+ editable ? /* @__PURE__ */ jsxs("div", { className: styles$4.header, contentEditable: false, children: [
404
672
  /* @__PURE__ */ jsxs(DropdownMenu.Root, { children: [
405
673
  /* @__PURE__ */ jsx(DropdownMenu.Trigger, { asChild: true, children: /* @__PURE__ */ jsxs(
406
674
  "button",
407
675
  {
408
676
  type: "button",
409
- className: styles$3.langTrigger,
677
+ className: styles$4.langTrigger,
410
678
  "aria-label": "Code language",
411
679
  children: [
412
680
  /* @__PURE__ */ jsx("span", { children: currentLabel }),
413
- /* @__PURE__ */ jsx(ChevronDownIcon, { size: 14, className: styles$3.langChevron })
681
+ /* @__PURE__ */ jsx(ChevronDownIcon, { size: 14, className: styles$4.langChevron })
414
682
  ]
415
683
  }
416
684
  ) }),
417
685
  /* @__PURE__ */ jsx(DropdownMenu.Portal, { children: /* @__PURE__ */ jsx(
418
686
  DropdownMenu.Content,
419
687
  {
420
- className: styles$3.langMenu,
688
+ className: styles$4.langMenu,
421
689
  sideOffset: 4,
422
690
  align: "end",
423
691
  children: LANGUAGES.map((l) => {
@@ -426,10 +694,10 @@ function CodeBlockView({
426
694
  return /* @__PURE__ */ jsxs(
427
695
  DropdownMenu.Item,
428
696
  {
429
- className: `${styles$3.langItem}${selected ? ` ${styles$3.langItemSelected}` : ""}`,
697
+ className: `${styles$4.langItem}${selected ? ` ${styles$4.langItemSelected}` : ""}`,
430
698
  onSelect: () => updateAttributes({ language: l.value }),
431
699
  children: [
432
- /* @__PURE__ */ jsx("span", { className: styles$3.langItemCheck, children: selected ? /* @__PURE__ */ jsx(CheckIcon, { size: 14 }) : null }),
700
+ /* @__PURE__ */ jsx("span", { className: styles$4.langItemCheck, children: selected ? /* @__PURE__ */ jsx(CheckIcon, { size: 14 }) : null }),
433
701
  optionLabel
434
702
  ]
435
703
  },
@@ -443,15 +711,18 @@ function CodeBlockView({
443
711
  "button",
444
712
  {
445
713
  type: "button",
446
- className: styles$3.deleteBtn,
714
+ className: styles$4.deleteBtn,
447
715
  title: labels.delete,
448
716
  "aria-label": labels.delete,
449
717
  onClick: () => deleteNode(),
450
718
  children: /* @__PURE__ */ jsx(TrashIcon, {})
451
719
  }
452
720
  )
453
- ] }),
454
- /* @__PURE__ */ jsx("pre", { className: styles$3.pre, children: /* @__PURE__ */ jsx(NodeViewContent, { as: "code" }) })
721
+ ] }) : (
722
+ // 只读:只展示语言标签,无下拉 / 删除等交互件
723
+ /* @__PURE__ */ jsx("div", { className: styles$4.langBadge, contentEditable: false, children: currentLabel })
724
+ ),
725
+ /* @__PURE__ */ jsx("pre", { className: styles$4.pre, children: /* @__PURE__ */ jsx(NodeViewContent, { as: "code" }) })
455
726
  ] });
456
727
  }
457
728
  const CodeBlock = CodeBlockLowlight.extend({
@@ -510,6 +781,7 @@ const ImageWithConfirmDelete = Image.extend({
510
781
  });
511
782
  const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
512
783
  initialMarkdown = "",
784
+ editable = true,
513
785
  sources,
514
786
  renderCitation,
515
787
  placeholder,
@@ -519,7 +791,12 @@ const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
519
791
  markdownFileDrop = true,
520
792
  extraExtensions,
521
793
  codeBlockLabels,
522
- className
794
+ className,
795
+ comments,
796
+ activeCommentId,
797
+ onCommentClick,
798
+ onActiveCommentChange,
799
+ showCommentGutter = true
523
800
  }, ref) {
524
801
  const preparedInitial = enrichMarkdownCitations(
525
802
  initialMarkdown,
@@ -531,6 +808,8 @@ const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
531
808
  CodeBlock.configure({ lowlight, codeBlockLabels }),
532
809
  ImageWithConfirmDelete.configure({ inline: false }),
533
810
  createCitationRef({ renderCitation }),
811
+ CommentMark,
812
+ commentAnchorExtension({ showGutter: showCommentGutter }),
534
813
  Markdown,
535
814
  TableOfContents.configure({
536
815
  getId: makeTocGetId(),
@@ -546,11 +825,12 @@ const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
546
825
  ],
547
826
  content: preparedInitial,
548
827
  contentType: "markdown",
828
+ editable,
549
829
  // Next.js SSR:服务端不立即渲染,避免 hydration 不一致
550
830
  immediatelyRender: false,
551
831
  editorProps: {
552
832
  attributes: {
553
- class: styles$4.editorContent,
833
+ class: styles$5.editorContent,
554
834
  "data-placeholder": placeholder ?? ""
555
835
  }
556
836
  }
@@ -559,6 +839,56 @@ const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
559
839
  onEditorReady == null ? void 0 : onEditorReady(editor);
560
840
  return () => onEditorReady == null ? void 0 : onEditorReady(null);
561
841
  }, [editor, onEditorReady]);
842
+ useEffect(() => {
843
+ editor == null ? void 0 : editor.setEditable(editable);
844
+ }, [editor, editable]);
845
+ const commentsSignatureRef = useRef("");
846
+ useEffect(() => {
847
+ if (!editor || !editable) return;
848
+ const signature = (comments ?? []).map((c) => `${c.commentId}:${c.segments.length}`).join("|");
849
+ if (signature === commentsSignatureRef.current) return;
850
+ commentsSignatureRef.current = signature;
851
+ applyCommentAnchorsToEditor(editor, comments ?? []);
852
+ }, [editor, editable, comments]);
853
+ useEffect(() => {
854
+ if (!editor) return;
855
+ editor.view.dispatch(
856
+ editor.state.tr.setMeta(
857
+ COMMENT_ACTIVE_META,
858
+ activeCommentId ?? null
859
+ )
860
+ );
861
+ }, [editor, activeCommentId]);
862
+ const onCommentClickRef = useRef(onCommentClick);
863
+ const onActiveCommentChangeRef = useRef(onActiveCommentChange);
864
+ onCommentClickRef.current = onCommentClick;
865
+ onActiveCommentChangeRef.current = onActiveCommentChange;
866
+ useEffect(() => {
867
+ if (!editor) return;
868
+ const onTransaction = ({
869
+ transaction
870
+ }) => {
871
+ var _a, _b, _c, _d;
872
+ const click = transaction.getMeta(COMMENT_CLICK_META);
873
+ if (click) {
874
+ (_a = onCommentClickRef.current) == null ? void 0 : _a.call(onCommentClickRef, click);
875
+ (_b = onActiveCommentChangeRef.current) == null ? void 0 : _b.call(onActiveCommentChangeRef, click.commentIds[0] ?? null);
876
+ }
877
+ const gutter = transaction.getMeta(COMMENT_GUTTER_META);
878
+ if (gutter) {
879
+ (_c = onCommentClickRef.current) == null ? void 0 : _c.call(onCommentClickRef, {
880
+ commentIds: gutter.commentIds,
881
+ anchorEl: null,
882
+ pos: gutter.pos
883
+ });
884
+ (_d = onActiveCommentChangeRef.current) == null ? void 0 : _d.call(onActiveCommentChangeRef, gutter.commentIds[0] ?? null);
885
+ }
886
+ };
887
+ editor.on("transaction", onTransaction);
888
+ return () => {
889
+ editor.off("transaction", onTransaction);
890
+ };
891
+ }, [editor]);
562
892
  useImperativeHandle(
563
893
  ref,
564
894
  () => ({
@@ -574,7 +904,10 @@ const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
574
904
  var _a;
575
905
  return ((_a = editor == null ? void 0 : editor.getJSON) == null ? void 0 : _a.call(editor)) ?? {};
576
906
  },
577
- getEditor: () => editor ?? null
907
+ getEditor: () => editor ?? null,
908
+ focusComment: (commentId) => editor ? focusComment(editor, commentId) : false,
909
+ nextComment: (dir) => editor ? nextComment(editor, dir ?? "next") : null,
910
+ getCommentIds: () => editor ? collectCommentIds(editor) : []
578
911
  }),
579
912
  [editor]
580
913
  );
@@ -582,7 +915,7 @@ const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
582
915
  EditorContent,
583
916
  {
584
917
  editor,
585
- className: className ? `${styles$4.editorScroll} ${className}` : styles$4.editorScroll
918
+ className: className ? `${styles$5.editorScroll} ${className}` : styles$5.editorScroll
586
919
  }
587
920
  );
588
921
  });
@@ -614,7 +947,7 @@ function MarkdownPreview({
614
947
  editable: false,
615
948
  immediatelyRender: false,
616
949
  editorProps: {
617
- attributes: { class: styles$4.editorContent }
950
+ attributes: { class: styles$5.editorContent }
618
951
  }
619
952
  },
620
953
  [extensions]
@@ -627,7 +960,7 @@ function MarkdownPreview({
627
960
  EditorContent,
628
961
  {
629
962
  editor,
630
- className: className ?? styles$4.editorScroll
963
+ className: className ?? styles$5.editorScroll
631
964
  }
632
965
  );
633
966
  }
@@ -656,8 +989,8 @@ const scriptGlyph = "_scriptGlyph_i2emf_203";
656
989
  const menu = "_menu_i2emf_215";
657
990
  const menuItem = "_menuItem_i2emf_226";
658
991
  const menuItemSelected = "_menuItemSelected_i2emf_252";
659
- const popoverContent = "_popoverContent_i2emf_266";
660
- const styles$2 = {
992
+ const popoverContent$1 = "_popoverContent_i2emf_266";
993
+ const styles$3 = {
661
994
  toolbar,
662
995
  inner,
663
996
  btn,
@@ -679,7 +1012,7 @@ const styles$2 = {
679
1012
  menu,
680
1013
  menuItem,
681
1014
  menuItemSelected,
682
- popoverContent
1015
+ popoverContent: popoverContent$1
683
1016
  };
684
1017
  const palette = "_palette_x5lrq_2";
685
1018
  const noneRow = "_noneRow_x5lrq_11";
@@ -690,7 +1023,7 @@ const swatch = "_swatch_x5lrq_54";
690
1023
  const swatchActive = "_swatchActive_x5lrq_70";
691
1024
  const themeLabel = "_themeLabel_x5lrq_76";
692
1025
  const themeRow = "_themeRow_x5lrq_84";
693
- const styles$1 = {
1026
+ const styles$2 = {
694
1027
  palette,
695
1028
  noneRow,
696
1029
  noneIcon,
@@ -713,46 +1046,46 @@ const THEME_COLORS = ["#ff6719", "#ff5500"];
713
1046
  function ColorPalette({ value, onPick, labels }) {
714
1047
  const t = { ...defaultColorPaletteLabels, ...labels };
715
1048
  const current = value == null ? void 0 : value.toLowerCase();
716
- return /* @__PURE__ */ jsxs("div", { className: styles$1.palette, children: [
1049
+ return /* @__PURE__ */ jsxs("div", { className: styles$2.palette, children: [
717
1050
  /* @__PURE__ */ jsxs(
718
1051
  "button",
719
1052
  {
720
1053
  type: "button",
721
- className: styles$1.noneRow,
1054
+ className: styles$2.noneRow,
722
1055
  onMouseDown: (e) => e.preventDefault(),
723
1056
  onClick: () => onPick(null),
724
1057
  children: [
725
- /* @__PURE__ */ jsx("span", { className: styles$1.noneIcon, "aria-hidden": true }),
726
- /* @__PURE__ */ jsx("span", { className: styles$1.noneLabel, children: t.none })
1058
+ /* @__PURE__ */ jsx("span", { className: styles$2.noneIcon, "aria-hidden": true }),
1059
+ /* @__PURE__ */ jsx("span", { className: styles$2.noneLabel, children: t.none })
727
1060
  ]
728
1061
  }
729
1062
  ),
730
- /* @__PURE__ */ jsx("div", { className: styles$1.grid, children: PALETTE.flat().map((c2) => /* @__PURE__ */ jsx(
1063
+ /* @__PURE__ */ jsx("div", { className: styles$2.grid, children: PALETTE.flat().map((c) => /* @__PURE__ */ jsx(
731
1064
  "button",
732
1065
  {
733
1066
  type: "button",
734
- className: `${styles$1.swatch} ${current === c2.toLowerCase() ? styles$1.swatchActive : ""}`,
735
- style: { background: c2 },
736
- title: c2,
737
- "aria-label": c2,
1067
+ className: `${styles$2.swatch} ${current === c.toLowerCase() ? styles$2.swatchActive : ""}`,
1068
+ style: { background: c },
1069
+ title: c,
1070
+ "aria-label": c,
738
1071
  onMouseDown: (e) => e.preventDefault(),
739
- onClick: () => onPick(c2)
1072
+ onClick: () => onPick(c)
740
1073
  },
741
- c2
1074
+ c
742
1075
  )) }),
743
- /* @__PURE__ */ jsx("div", { className: styles$1.themeLabel, children: t.theme }),
744
- /* @__PURE__ */ jsx("div", { className: styles$1.themeRow, children: THEME_COLORS.map((c2) => /* @__PURE__ */ jsx(
1076
+ /* @__PURE__ */ jsx("div", { className: styles$2.themeLabel, children: t.theme }),
1077
+ /* @__PURE__ */ jsx("div", { className: styles$2.themeRow, children: THEME_COLORS.map((c) => /* @__PURE__ */ jsx(
745
1078
  "button",
746
1079
  {
747
1080
  type: "button",
748
- className: `${styles$1.swatch} ${current === c2.toLowerCase() ? styles$1.swatchActive : ""}`,
749
- style: { background: c2 },
750
- title: c2,
751
- "aria-label": c2,
1081
+ className: `${styles$2.swatch} ${current === c.toLowerCase() ? styles$2.swatchActive : ""}`,
1082
+ style: { background: c },
1083
+ title: c,
1084
+ "aria-label": c,
752
1085
  onMouseDown: (e) => e.preventDefault(),
753
- onClick: () => onPick(c2)
1086
+ onClick: () => onPick(c)
754
1087
  },
755
- c2
1088
+ c
756
1089
  )) })
757
1090
  ] });
758
1091
  }
@@ -771,7 +1104,7 @@ function ToolbarButton({
771
1104
  "aria-label": title,
772
1105
  "aria-pressed": active2,
773
1106
  disabled,
774
- className: `${styles$2.btn} ${active2 ? styles$2.btnActive : ""}`,
1107
+ className: `${styles$3.btn} ${active2 ? styles$3.btnActive : ""}`,
775
1108
  onMouseDown: (e) => e.preventDefault(),
776
1109
  onClick,
777
1110
  children
@@ -779,7 +1112,7 @@ function ToolbarButton({
779
1112
  );
780
1113
  }
781
1114
  function Divider() {
782
- return /* @__PURE__ */ jsx("span", { className: styles$2.divider, "aria-hidden": true });
1115
+ return /* @__PURE__ */ jsx("span", { className: styles$3.divider, "aria-hidden": true });
783
1116
  }
784
1117
  const MenuCloseCtx = createContext(() => {
785
1118
  });
@@ -794,7 +1127,7 @@ function MenuPopover({
794
1127
  /* @__PURE__ */ jsx(Popover.Portal, { children: /* @__PURE__ */ jsx(
795
1128
  Popover.Content,
796
1129
  {
797
- className: styles$2.menu,
1130
+ className: styles$3.menu,
798
1131
  sideOffset: 4,
799
1132
  align: "start",
800
1133
  onOpenAutoFocus: (e) => e.preventDefault(),
@@ -816,7 +1149,7 @@ function MenuItem({
816
1149
  {
817
1150
  type: "button",
818
1151
  disabled,
819
- className: `${styles$2.menuItem} ${selected ? styles$2.menuItemSelected : ""}`,
1152
+ className: `${styles$3.menuItem} ${selected ? styles$3.menuItemSelected : ""}`,
820
1153
  onMouseDown: (e) => e.preventDefault(),
821
1154
  onClick: () => {
822
1155
  onSelect();
@@ -840,20 +1173,20 @@ function ColorPopover({
840
1173
  "button",
841
1174
  {
842
1175
  type: "button",
843
- className: styles$2.btn,
1176
+ className: styles$3.btn,
844
1177
  title,
845
1178
  "aria-label": title,
846
1179
  onMouseDown: (e) => e.preventDefault(),
847
- children: /* @__PURE__ */ jsxs("span", { className: styles$2.colorIcon, children: [
848
- /* @__PURE__ */ jsx("span", { className: styles$2.colorIconGlyph, children: glyph }),
849
- /* @__PURE__ */ jsx("span", { className: styles$2.colorIconBar, style: { background: bar } })
1180
+ children: /* @__PURE__ */ jsxs("span", { className: styles$3.colorIcon, children: [
1181
+ /* @__PURE__ */ jsx("span", { className: styles$3.colorIconGlyph, children: glyph }),
1182
+ /* @__PURE__ */ jsx("span", { className: styles$3.colorIconBar, style: { background: bar } })
850
1183
  ] })
851
1184
  }
852
1185
  ) }),
853
1186
  /* @__PURE__ */ jsx(Popover.Portal, { children: /* @__PURE__ */ jsx(
854
1187
  Popover.Content,
855
1188
  {
856
- className: styles$2.popoverContent,
1189
+ className: styles$3.popoverContent,
857
1190
  sideOffset: 4,
858
1191
  align: "start",
859
1192
  onOpenAutoFocus: (e) => e.preventDefault(),
@@ -862,8 +1195,8 @@ function ColorPopover({
862
1195
  ColorPalette,
863
1196
  {
864
1197
  value,
865
- onPick: (c2) => {
866
- onPick(c2);
1198
+ onPick: (c) => {
1199
+ onPick(c);
867
1200
  setOpen(false);
868
1201
  },
869
1202
  labels: paletteLabels
@@ -939,8 +1272,8 @@ function EditorToolbar({
939
1272
  if (!coords) return;
940
1273
  const $pos = editor.state.doc.resolve(coords.pos);
941
1274
  let inTable = false;
942
- for (let d2 = $pos.depth; d2 > 0; d2--) {
943
- if ($pos.node(d2).type.name === "table") {
1275
+ for (let d = $pos.depth; d > 0; d--) {
1276
+ if ($pos.node(d).type.name === "table") {
944
1277
  inTable = true;
945
1278
  break;
946
1279
  }
@@ -1031,12 +1364,12 @@ function EditorToolbar({
1031
1364
  };
1032
1365
  const canEditFontSize = editorFocused && state.isParagraph;
1033
1366
  const scriptActive = state.superscript ? "superscript" : state.subscript ? "subscript" : "normal";
1034
- return /* @__PURE__ */ jsxs(Fragment, { children: [
1367
+ return /* @__PURE__ */ jsxs(Fragment$1, { children: [
1035
1368
  /* @__PURE__ */ jsx(
1036
1369
  "div",
1037
1370
  {
1038
- className: className ? `${styles$2.toolbar} ${className}` : styles$2.toolbar,
1039
- children: /* @__PURE__ */ jsxs("div", { className: styles$2.inner, children: [
1371
+ className: className ? `${styles$3.toolbar} ${className}` : styles$3.toolbar,
1372
+ children: /* @__PURE__ */ jsxs("div", { className: styles$3.inner, children: [
1040
1373
  /* @__PURE__ */ jsx(
1041
1374
  ToolbarButton,
1042
1375
  {
@@ -1063,12 +1396,12 @@ function EditorToolbar({
1063
1396
  "button",
1064
1397
  {
1065
1398
  type: "button",
1066
- className: styles$2.styleTrigger,
1399
+ className: styles$3.styleTrigger,
1067
1400
  title: t.style,
1068
1401
  onMouseDown: (e) => e.preventDefault(),
1069
1402
  children: [
1070
- /* @__PURE__ */ jsx("span", { className: styles$2.styleTriggerLabel, children: t.style }),
1071
- /* @__PURE__ */ jsx(ChevronDownIcon, { size: 12, className: styles$2.styleTriggerCaret })
1403
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleTriggerLabel, children: t.style }),
1404
+ /* @__PURE__ */ jsx(ChevronDownIcon, { size: 12, className: styles$3.styleTriggerCaret })
1072
1405
  ]
1073
1406
  }
1074
1407
  ),
@@ -1078,8 +1411,8 @@ function EditorToolbar({
1078
1411
  {
1079
1412
  selected: (state.headingLevel ?? 0) === 0,
1080
1413
  onSelect: () => setBlockStyle(0),
1081
- children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1082
- /* @__PURE__ */ jsx("span", { className: styles$2.styleIcon, children: "¶" }),
1414
+ children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1415
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleIcon, children: "¶" }),
1083
1416
  t.normalText
1084
1417
  ] })
1085
1418
  }
@@ -1089,8 +1422,8 @@ function EditorToolbar({
1089
1422
  {
1090
1423
  selected: state.headingLevel === lv,
1091
1424
  onSelect: () => setBlockStyle(lv),
1092
- children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1093
- /* @__PURE__ */ jsx("span", { className: styles$2.styleIcon, children: `H${lv}` }),
1425
+ children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1426
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleIcon, children: `H${lv}` }),
1094
1427
  t.headingLabel(lv)
1095
1428
  ] })
1096
1429
  },
@@ -1106,14 +1439,14 @@ function EditorToolbar({
1106
1439
  "button",
1107
1440
  {
1108
1441
  type: "button",
1109
- className: styles$2.styleTrigger,
1442
+ className: styles$3.styleTrigger,
1110
1443
  title: t.fontSize,
1111
1444
  "aria-label": t.fontSize,
1112
1445
  disabled: !canEditFontSize,
1113
1446
  onMouseDown: (e) => e.preventDefault(),
1114
1447
  children: [
1115
- /* @__PURE__ */ jsx("span", { className: styles$2.styleTriggerLabel, children: state.fontSize || t.fontSize }),
1116
- /* @__PURE__ */ jsx(ChevronDownIcon, { size: 12, className: styles$2.styleTriggerCaret })
1448
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleTriggerLabel, children: state.fontSize || t.fontSize }),
1449
+ /* @__PURE__ */ jsx(ChevronDownIcon, { size: 12, className: styles$3.styleTriggerCaret })
1117
1450
  ]
1118
1451
  }
1119
1452
  ),
@@ -1123,8 +1456,8 @@ function EditorToolbar({
1123
1456
  {
1124
1457
  selected: !state.fontSize,
1125
1458
  onSelect: () => applyFontSize(""),
1126
- children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1127
- /* @__PURE__ */ jsx("span", { className: styles$2.styleIcon, children: "A" }),
1459
+ children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1460
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleIcon, children: "A" }),
1128
1461
  t.fontSizeDefault
1129
1462
  ] })
1130
1463
  }
@@ -1134,8 +1467,8 @@ function EditorToolbar({
1134
1467
  {
1135
1468
  selected: state.fontSize === size,
1136
1469
  onSelect: () => applyFontSize(size),
1137
- children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1138
- /* @__PURE__ */ jsx("span", { className: styles$2.styleIcon, children: parseInt(size, 10) }),
1470
+ children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1471
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleIcon, children: parseInt(size, 10) }),
1139
1472
  size
1140
1473
  ] })
1141
1474
  },
@@ -1219,13 +1552,13 @@ function EditorToolbar({
1219
1552
  "button",
1220
1553
  {
1221
1554
  type: "button",
1222
- className: `${styles$2.scriptTrigger} ${scriptActive !== "normal" ? styles$2.btnActive : ""}`,
1555
+ className: `${styles$3.scriptTrigger} ${scriptActive !== "normal" ? styles$3.btnActive : ""}`,
1223
1556
  title: t.scriptMenu,
1224
1557
  "aria-label": t.scriptMenu,
1225
1558
  onMouseDown: (e) => e.preventDefault(),
1226
1559
  children: [
1227
- /* @__PURE__ */ jsx("span", { className: styles$2.scriptTriggerGlyph, children: "A" }),
1228
- /* @__PURE__ */ jsx(ChevronDownIcon, { size: 12, className: styles$2.styleTriggerCaret })
1560
+ /* @__PURE__ */ jsx("span", { className: styles$3.scriptTriggerGlyph, children: "A" }),
1561
+ /* @__PURE__ */ jsx(ChevronDownIcon, { size: 12, className: styles$3.styleTriggerCaret })
1229
1562
  ]
1230
1563
  }
1231
1564
  ),
@@ -1235,8 +1568,8 @@ function EditorToolbar({
1235
1568
  {
1236
1569
  selected: scriptActive === "normal",
1237
1570
  onSelect: () => chain().unsetSuperscript().unsetSubscript().run(),
1238
- children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1239
- /* @__PURE__ */ jsx("span", { className: styles$2.styleIcon, children: "A" }),
1571
+ children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1572
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleIcon, children: "A" }),
1240
1573
  t.scriptNormal
1241
1574
  ] })
1242
1575
  }
@@ -1246,8 +1579,8 @@ function EditorToolbar({
1246
1579
  {
1247
1580
  selected: scriptActive === "superscript",
1248
1581
  onSelect: () => chain().unsetSubscript().toggleSuperscript().run(),
1249
- children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1250
- /* @__PURE__ */ jsxs("span", { className: `${styles$2.styleIcon} ${styles$2.scriptGlyph}`, children: [
1582
+ children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1583
+ /* @__PURE__ */ jsxs("span", { className: `${styles$3.styleIcon} ${styles$3.scriptGlyph}`, children: [
1251
1584
  "x",
1252
1585
  /* @__PURE__ */ jsx("sup", { children: "2" })
1253
1586
  ] }),
@@ -1260,8 +1593,8 @@ function EditorToolbar({
1260
1593
  {
1261
1594
  selected: scriptActive === "subscript",
1262
1595
  onSelect: () => chain().unsetSuperscript().toggleSubscript().run(),
1263
- children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1264
- /* @__PURE__ */ jsxs("span", { className: `${styles$2.styleIcon} ${styles$2.scriptGlyph}`, children: [
1596
+ children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1597
+ /* @__PURE__ */ jsxs("span", { className: `${styles$3.styleIcon} ${styles$3.scriptGlyph}`, children: [
1265
1598
  "x",
1266
1599
  /* @__PURE__ */ jsx("sub", { children: "2" })
1267
1600
  ] }),
@@ -1274,7 +1607,7 @@ function EditorToolbar({
1274
1607
  ),
1275
1608
  /* @__PURE__ */ jsx(Divider, {}),
1276
1609
  /* @__PURE__ */ jsx(ToolbarButton, { title: t.link, active: state.link, onClick: toggleLink, children: /* @__PURE__ */ jsx(LinkIcon, {}) }),
1277
- onImageUpload ? /* @__PURE__ */ jsxs(Fragment, { children: [
1610
+ onImageUpload ? /* @__PURE__ */ jsxs(Fragment$1, { children: [
1278
1611
  /* @__PURE__ */ jsx(ToolbarButton, { title: t.image, onClick: handlePickImage, children: /* @__PURE__ */ jsx(ImageIcon, {}) }),
1279
1612
  /* @__PURE__ */ jsx(
1280
1613
  "input",
@@ -1293,7 +1626,7 @@ function EditorToolbar({
1293
1626
  title: t.blockquote,
1294
1627
  active: state.blockquote,
1295
1628
  onClick: () => chain().toggleBlockquote().run(),
1296
- children: /* @__PURE__ */ jsx("span", { className: styles$2.txtIcon, children: "❝" })
1629
+ children: /* @__PURE__ */ jsx("span", { className: styles$3.txtIcon, children: "❝" })
1297
1630
  }
1298
1631
  ),
1299
1632
  /* @__PURE__ */ jsx(Divider, {}),
@@ -1332,22 +1665,22 @@ function EditorToolbar({
1332
1665
  "button",
1333
1666
  {
1334
1667
  type: "button",
1335
- className: styles$2.styleTrigger,
1668
+ className: styles$3.styleTrigger,
1336
1669
  title: t.more,
1337
1670
  onMouseDown: (e) => e.preventDefault(),
1338
1671
  children: [
1339
- /* @__PURE__ */ jsx("span", { className: styles$2.styleTriggerLabel, children: t.more }),
1340
- /* @__PURE__ */ jsx(ChevronDownIcon, { size: 12, className: styles$2.styleTriggerCaret })
1672
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleTriggerLabel, children: t.more }),
1673
+ /* @__PURE__ */ jsx(ChevronDownIcon, { size: 12, className: styles$3.styleTriggerCaret })
1341
1674
  ]
1342
1675
  }
1343
1676
  ),
1344
1677
  children: [
1345
- /* @__PURE__ */ jsx(MenuItem, { onSelect: () => chain().toggleCodeBlock().run(), children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1346
- /* @__PURE__ */ jsx("span", { className: styles$2.styleIcon, children: "{ }" }),
1678
+ /* @__PURE__ */ jsx(MenuItem, { onSelect: () => chain().toggleCodeBlock().run(), children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1679
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleIcon, children: "{ }" }),
1347
1680
  t.codeBlock
1348
1681
  ] }) }),
1349
- /* @__PURE__ */ jsx(MenuItem, { onSelect: () => chain().setHorizontalRule().run(), children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1350
- /* @__PURE__ */ jsx("span", { className: styles$2.styleIcon, children: "—" }),
1682
+ /* @__PURE__ */ jsx(MenuItem, { onSelect: () => chain().setHorizontalRule().run(), children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1683
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleIcon, children: "—" }),
1351
1684
  t.hr
1352
1685
  ] }) }),
1353
1686
  /* @__PURE__ */ jsx(
@@ -1355,8 +1688,8 @@ function EditorToolbar({
1355
1688
  {
1356
1689
  disabled: state.inTable,
1357
1690
  onSelect: () => chain().insertTable({ rows: 3, cols: 3, withHeaderRow: true }).run(),
1358
- children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1359
- /* @__PURE__ */ jsx("span", { className: styles$2.styleIcon, children: "⊞" }),
1691
+ children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1692
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleIcon, children: "⊞" }),
1360
1693
  t.tableInsert
1361
1694
  ] })
1362
1695
  }
@@ -1364,8 +1697,8 @@ function EditorToolbar({
1364
1697
  /* @__PURE__ */ jsx(MenuItem, { onSelect: () => {
1365
1698
  var _a;
1366
1699
  return (_a = mdFileInputRef.current) == null ? void 0 : _a.click();
1367
- }, children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1368
- /* @__PURE__ */ jsx("span", { className: styles$2.styleIcon, children: "M↓" }),
1700
+ }, children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1701
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleIcon, children: "M↓" }),
1369
1702
  t.importMarkdown
1370
1703
  ] }) }),
1371
1704
  extraToolbarItems == null ? void 0 : extraToolbarItems.map((item2) => /* @__PURE__ */ jsx(
@@ -1373,8 +1706,8 @@ function EditorToolbar({
1373
1706
  {
1374
1707
  disabled: item2.disabled,
1375
1708
  onSelect: () => item2.onSelect(editor),
1376
- children: /* @__PURE__ */ jsxs("span", { className: styles$2.styleItem, children: [
1377
- /* @__PURE__ */ jsx("span", { className: styles$2.styleIcon, children: item2.icon }),
1709
+ children: /* @__PURE__ */ jsxs("span", { className: styles$3.styleItem, children: [
1710
+ /* @__PURE__ */ jsx("span", { className: styles$3.styleIcon, children: item2.icon }),
1378
1711
  item2.label
1379
1712
  ] })
1380
1713
  },
@@ -1400,7 +1733,7 @@ function EditorToolbar({
1400
1733
  /* @__PURE__ */ jsxs(
1401
1734
  "div",
1402
1735
  {
1403
- className: styles$2.tableBubble,
1736
+ className: styles$3.tableBubble,
1404
1737
  style: { position: "fixed", left: tableMenu.x, top: tableMenu.y },
1405
1738
  onMouseDown: (e) => e.stopPropagation(),
1406
1739
  onContextMenu: (e) => e.preventDefault(),
@@ -1492,7 +1825,7 @@ const chevron = "_chevron_euqdt_159";
1492
1825
  const chevronUp = "_chevronUp_euqdt_166";
1493
1826
  const mobilePanel = "_mobilePanel_euqdt_170";
1494
1827
  const mobilePanelOpen = "_mobilePanelOpen_euqdt_176";
1495
- const styles = {
1828
+ const styles$1 = {
1496
1829
  desktop,
1497
1830
  header,
1498
1831
  headerTitle,
@@ -1534,17 +1867,17 @@ function TocPanel({ items, activeId, onItemClick, labels }) {
1534
1867
  });
1535
1868
  }, [activeId]);
1536
1869
  if (!items.length) return null;
1537
- const minLevel = Math.min(...items.map((i) => i.level));
1870
+ const minLevel = Math.min(...items.map((i2) => i2.level));
1538
1871
  const handleClick = (item2) => {
1539
1872
  if (item2.locked) return;
1540
1873
  onItemClick == null ? void 0 : onItemClick(item2);
1541
1874
  if (isMobile) setMobileOpen(false);
1542
1875
  };
1543
- const list2 = /* @__PURE__ */ jsx("ul", { className: styles.list, children: items.map((item2) => /* @__PURE__ */ jsx("li", { children: /* @__PURE__ */ jsxs(
1876
+ const list2 = /* @__PURE__ */ jsx("ul", { className: styles$1.list, children: items.map((item2) => /* @__PURE__ */ jsx("li", { children: /* @__PURE__ */ jsxs(
1544
1877
  "a",
1545
1878
  {
1546
1879
  href: item2.locked ? void 0 : `#${item2.id}`,
1547
- className: `${styles.item} ${item2.id === activeId ? styles.active : ""} ${item2.locked ? styles.locked : ""}`,
1880
+ className: `${styles$1.item} ${item2.id === activeId ? styles$1.active : ""} ${item2.locked ? styles$1.locked : ""}`,
1548
1881
  style: { paddingLeft: `${(item2.level - minLevel) * 12 + 12}px` },
1549
1882
  "aria-current": item2.id === activeId ? "true" : void 0,
1550
1883
  "aria-disabled": item2.locked ? "true" : void 0,
@@ -1553,27 +1886,27 @@ function TocPanel({ items, activeId, onItemClick, labels }) {
1553
1886
  handleClick(item2);
1554
1887
  },
1555
1888
  children: [
1556
- /* @__PURE__ */ jsx("span", { className: styles.itemText, children: item2.text }),
1557
- item2.locked ? /* @__PURE__ */ jsx(LockIcon, { className: styles.lockIcon, "aria-hidden": true }) : null
1889
+ /* @__PURE__ */ jsx("span", { className: styles$1.itemText, children: item2.text }),
1890
+ item2.locked ? /* @__PURE__ */ jsx(LockIcon, { className: styles$1.lockIcon, "aria-hidden": true }) : null
1558
1891
  ]
1559
1892
  }
1560
1893
  ) }, item2.id)) });
1561
1894
  if (isMobile) {
1562
- return /* @__PURE__ */ jsxs("nav", { className: styles.mobile, "aria-label": t.title, children: [
1895
+ return /* @__PURE__ */ jsxs("nav", { className: styles$1.mobile, "aria-label": t.title, children: [
1563
1896
  /* @__PURE__ */ jsxs(
1564
1897
  "button",
1565
1898
  {
1566
1899
  type: "button",
1567
- className: styles.mobileBar,
1900
+ className: styles$1.mobileBar,
1568
1901
  "aria-expanded": mobileOpen,
1569
1902
  onClick: () => setMobileOpen((v) => !v),
1570
1903
  children: [
1571
- /* @__PURE__ */ jsx(MenuIcon, { className: styles.mobileBarIcon, "aria-hidden": true }),
1904
+ /* @__PURE__ */ jsx(MenuIcon, { className: styles$1.mobileBarIcon, "aria-hidden": true }),
1572
1905
  /* @__PURE__ */ jsx("span", { children: t.title }),
1573
1906
  /* @__PURE__ */ jsx(
1574
1907
  "span",
1575
1908
  {
1576
- className: `${styles.chevron} ${mobileOpen ? styles.chevronUp : ""}`,
1909
+ className: `${styles$1.chevron} ${mobileOpen ? styles$1.chevronUp : ""}`,
1577
1910
  "aria-hidden": true,
1578
1911
  children: /* @__PURE__ */ jsx(ChevronDownIcon, { size: 16 })
1579
1912
  }
@@ -1585,7 +1918,7 @@ function TocPanel({ items, activeId, onItemClick, labels }) {
1585
1918
  "div",
1586
1919
  {
1587
1920
  ref: mobilePanelRef,
1588
- className: `${styles.mobilePanel} ${mobileOpen ? styles.mobilePanelOpen : ""}`,
1921
+ className: `${styles$1.mobilePanel} ${mobileOpen ? styles$1.mobilePanelOpen : ""}`,
1589
1922
  children: list2
1590
1923
  }
1591
1924
  )
@@ -1596,7 +1929,7 @@ function TocPanel({ items, activeId, onItemClick, labels }) {
1596
1929
  "button",
1597
1930
  {
1598
1931
  type: "button",
1599
- className: styles.collapsedRail,
1932
+ className: styles$1.collapsedRail,
1600
1933
  "aria-label": t.expand,
1601
1934
  title: t.expand,
1602
1935
  onClick: () => setCollapsed(false),
@@ -1604,14 +1937,14 @@ function TocPanel({ items, activeId, onItemClick, labels }) {
1604
1937
  }
1605
1938
  );
1606
1939
  }
1607
- return /* @__PURE__ */ jsxs("nav", { className: styles.desktop, "aria-label": t.title, ref: desktopNavRef, children: [
1608
- /* @__PURE__ */ jsxs("div", { className: styles.header, children: [
1609
- /* @__PURE__ */ jsx("span", { className: styles.headerTitle, children: t.title }),
1940
+ return /* @__PURE__ */ jsxs("nav", { className: styles$1.desktop, "aria-label": t.title, ref: desktopNavRef, children: [
1941
+ /* @__PURE__ */ jsxs("div", { className: styles$1.header, children: [
1942
+ /* @__PURE__ */ jsx("span", { className: styles$1.headerTitle, children: t.title }),
1610
1943
  /* @__PURE__ */ jsx(
1611
1944
  "button",
1612
1945
  {
1613
1946
  type: "button",
1614
- className: styles.collapseBtn,
1947
+ className: styles$1.collapseBtn,
1615
1948
  "aria-label": t.collapse,
1616
1949
  title: t.collapse,
1617
1950
  onClick: () => setCollapsed(true),
@@ -1736,8 +2069,49 @@ function scrollToTocHeading(headingId, scrollContainer, options) {
1736
2069
  };
1737
2070
  requestAnimationFrame(animate);
1738
2071
  }
2072
+ const popoverAnchor = "_popoverAnchor_ztxwe_57";
2073
+ const popoverContent = "_popoverContent_ztxwe_64";
2074
+ const styles = {
2075
+ popoverAnchor,
2076
+ popoverContent
2077
+ };
2078
+ function CommentPopover({
2079
+ open,
2080
+ onOpenChange,
2081
+ anchorEl,
2082
+ children,
2083
+ side = "top",
2084
+ align = "start",
2085
+ sideOffset = 6
2086
+ }) {
2087
+ const rect = open && anchorEl ? anchorEl.getBoundingClientRect() : null;
2088
+ return /* @__PURE__ */ jsxs(Popover.Root, { open, onOpenChange, children: [
2089
+ rect && /* @__PURE__ */ jsx(Popover.Anchor, { asChild: true, children: /* @__PURE__ */ jsx(
2090
+ "span",
2091
+ {
2092
+ className: styles.popoverAnchor,
2093
+ style: { left: rect.left, top: rect.top }
2094
+ }
2095
+ ) }),
2096
+ /* @__PURE__ */ jsx(Popover.Portal, { children: /* @__PURE__ */ jsx(
2097
+ Popover.Content,
2098
+ {
2099
+ className: styles.popoverContent,
2100
+ side,
2101
+ align,
2102
+ sideOffset,
2103
+ onOpenAutoFocus: (e) => e.preventDefault(),
2104
+ onCloseAutoFocus: (e) => e.preventDefault(),
2105
+ children
2106
+ }
2107
+ ) })
2108
+ ] });
2109
+ }
1739
2110
  export {
1740
2111
  BoldIcon,
2112
+ COMMENT_ACTIVE_META,
2113
+ COMMENT_CLICK_META,
2114
+ COMMENT_GUTTER_META,
1741
2115
  CheckIcon,
1742
2116
  ChevronDownIcon,
1743
2117
  CitationInteractive,
@@ -1748,6 +2122,8 @@ export {
1748
2122
  ColumnAfterIcon,
1749
2123
  ColumnBeforeIcon,
1750
2124
  ColumnDeleteIcon,
2125
+ CommentMark,
2126
+ CommentPopover,
1751
2127
  EditorToolbar,
1752
2128
  ImageIcon,
1753
2129
  ItalicIcon,
@@ -1772,24 +2148,37 @@ export {
1772
2148
  TrashIcon,
1773
2149
  UnderlineIcon,
1774
2150
  UndoIcon,
1775
- c as applyCitationSources,
2151
+ g as applyCitationSources,
2152
+ applyCommentAnchorsToEditor,
1776
2153
  baseExtensions,
2154
+ h as blockTextHash,
2155
+ collectCommentIds,
2156
+ commentAnchorExtension,
2157
+ commentAnchorPlugin,
2158
+ commentAnchorPluginKey,
2159
+ commentRangesById,
1777
2160
  createCitationRef,
1778
2161
  defaultCodeBlockLabels,
1779
2162
  defaultColorPaletteLabels,
2163
+ defaultCommentLabels,
1780
2164
  defaultTocLabels,
1781
2165
  defaultToolbarLabels,
1782
2166
  enrichMarkdownCitations,
1783
- d as extractToc,
2167
+ i as extractToc,
1784
2168
  findCitationRefElement,
2169
+ focusComment,
1785
2170
  insertMarkdown,
1786
2171
  looksLikeMarkdown,
1787
2172
  lowlight,
1788
2173
  makeTocGetId,
2174
+ mapCommentAnchors,
2175
+ mergeCommentIntervals,
2176
+ nextComment,
1789
2177
  pureCodeBlock,
1790
2178
  pureImage,
1791
2179
  readCitationAttrs,
1792
2180
  scrollToTocHeading,
2181
+ stripCommentAnchorMarks,
1793
2182
  useIsMobile
1794
2183
  };
1795
2184
  //# sourceMappingURL=index.js.map