tiptap-markdown-react 0.11.0 → 0.12.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.
package/dist/index.js CHANGED
@@ -1,7 +1,7 @@
1
1
  "use client";
2
2
  import { Markdown, MarkdownManager } from "@tiptap/markdown";
3
- import { c as renderOrUpdateChart, d as destroyChart } from "./scrollToTocHeading-EkePiWil.js";
4
- import { C, a, R, b, f, m, r, s } from "./scrollToTocHeading-EkePiWil.js";
3
+ import { c as renderOrUpdateChart, d as destroyChart } from "./scrollToTocHeading-DVdii3VR.js";
4
+ import { C, a, R, b, f, m, r, s } from "./scrollToTocHeading-DVdii3VR.js";
5
5
  import { jsx, jsxs, Fragment as Fragment$1 } from "react/jsx-runtime";
6
6
  import CodeBlockLowlight from "@tiptap/extension-code-block-lowlight";
7
7
  import FindAndReplace, { FindAndReplacePluginKey, createSearchRegex } from "@tiptap/extension-find-and-replace";
@@ -9,11 +9,12 @@ import { default as default2 } from "@tiptap/extension-find-and-replace";
9
9
  import Image from "@tiptap/extension-image";
10
10
  import { TableOfContents } from "@tiptap/extension-table-of-contents";
11
11
  import { NodeViewWrapper, ReactNodeViewRenderer, useEditorState, NodeViewContent, useEditor, EditorContent } from "@tiptap/react";
12
- import { useState, useRef, useCallback, useEffect, useMemo, forwardRef, useImperativeHandle, useId, useContext, createContext } from "react";
13
- import { e as enrichMarkdownCitations, b as styles$6 } from "./ReportContent-By-tSiNn.js";
14
- import { R as R2, a as a2, s as s2 } from "./ReportContent-By-tSiNn.js";
15
- import { C as CitationRef, i as mergeCommentIntervals, h as mapCommentAnchors, p as prepareChartMarkdown, j as reportChart, b as baseExtensions, f as CommentMark, l as lowlight, m as makeTocGetId, k as parseCodeTokenAsChartOrCodeBlock, a as pureCodeBlock, c as pureImage, n as renderMathInto, o as subscribeMathClick, d as pureChart } from "./extractToc-CB4RYsMJ.js";
16
- import { g, e, s as s3 } from "./extractToc-CB4RYsMJ.js";
12
+ import { createPortal } from "react-dom";
13
+ import { useState, useEffect, useCallback, useRef, useMemo, forwardRef, useImperativeHandle, useId, useContext, createContext } from "react";
14
+ import { e as enrichMarkdownCitations, b as styles$6 } from "./ReportContent-CfvE4CYH.js";
15
+ import { R as R2, a as a2, s as s2 } from "./ReportContent-CfvE4CYH.js";
16
+ import { C as CitationRef, i as mergeCommentIntervals, h as mapCommentAnchors, p as prepareChartMarkdown, j as reportChart, b as baseExtensions, f as CommentMark, l as lowlight, m as makeTocGetId, k as parseCodeTokenAsChartOrCodeBlock, a as pureCodeBlock, c as pureImage, n as renderMathInto, o as subscribeMathClick, d as pureChart } from "./extractToc-BT3OquOq.js";
17
+ import { g, e, s as s3 } from "./extractToc-BT3OquOq.js";
17
18
  import { Slice, Fragment } from "@tiptap/pm/model";
18
19
  import { Extension, Node as Node$1 } from "@tiptap/core";
19
20
  import { PluginKey, Plugin, NodeSelection, TextSelection } from "@tiptap/pm/state";
@@ -23,7 +24,6 @@ import { skipTrailingNodeMeta } from "@tiptap/extensions";
23
24
  import { CellSelection, isInTable, selectedRect, rowIsHeader } from "@tiptap/pm/tables";
24
25
  import * as DropdownMenu from "@radix-ui/react-dropdown-menu";
25
26
  import * as Popover from "@radix-ui/react-popover";
26
- import { createPortal } from "react-dom";
27
27
  function CitationRefView({ node, extension }) {
28
28
  const index = String(node.attrs.index ?? "");
29
29
  const url = node.attrs.url || null;
@@ -462,6 +462,26 @@ const XIcon = (p) => /* @__PURE__ */ jsxs(Svg, { ...p, children: [
462
462
  /* @__PURE__ */ jsx("path", { d: "m6 6 12 12" })
463
463
  ] });
464
464
  const ChevronUpIcon = (p) => /* @__PURE__ */ jsx(Svg, { ...p, children: /* @__PURE__ */ jsx("path", { d: "m18 15-6-6-6 6" }) });
465
+ const ReplaceIcon = (p) => /* @__PURE__ */ jsxs(Svg, { ...p, children: [
466
+ /* @__PURE__ */ jsx("path", { d: "M14 4a1 1 0 0 1 1-1" }),
467
+ /* @__PURE__ */ jsx("path", { d: "M15 10a1 1 0 0 1-1-1" }),
468
+ /* @__PURE__ */ jsx("path", { d: "M21 4a1 1 0 0 0-1-1" }),
469
+ /* @__PURE__ */ jsx("path", { d: "M21 9a1 1 0 0 1-1 1" }),
470
+ /* @__PURE__ */ jsx("path", { d: "m3 7 3 3 3-3" }),
471
+ /* @__PURE__ */ jsx("path", { d: "M6 10V5a2 2 0 0 1 2-2h2" }),
472
+ /* @__PURE__ */ jsx("rect", { x: "3", y: "14", width: "7", height: "7", rx: "1" })
473
+ ] });
474
+ const ReplaceAllIcon = (p) => /* @__PURE__ */ jsxs(Svg, { ...p, children: [
475
+ /* @__PURE__ */ jsx("path", { d: "M14 14a1 1 0 0 1 1 1v5a1 1 0 0 1-1 1" }),
476
+ /* @__PURE__ */ jsx("path", { d: "M14 4a1 1 0 0 1 1-1" }),
477
+ /* @__PURE__ */ jsx("path", { d: "M15 10a1 1 0 0 1-1-1" }),
478
+ /* @__PURE__ */ jsx("path", { d: "M19 14a1 1 0 0 1 1 1v5a1 1 0 0 1-1 1" }),
479
+ /* @__PURE__ */ jsx("path", { d: "M21 4a1 1 0 0 0-1-1" }),
480
+ /* @__PURE__ */ jsx("path", { d: "M21 9a1 1 0 0 1-1 1" }),
481
+ /* @__PURE__ */ jsx("path", { d: "m3 7 3 3 3-3" }),
482
+ /* @__PURE__ */ jsx("path", { d: "M6 10V5a2 2 0 0 1 2-2h2" }),
483
+ /* @__PURE__ */ jsx("rect", { x: "3", y: "14", width: "7", height: "7", rx: "1" })
484
+ ] });
465
485
  const ColumnBeforeIcon = (p) => /* @__PURE__ */ jsxs(Svg, { ...p, children: [
466
486
  /* @__PURE__ */ jsx("rect", { x: "10", y: "4", width: "11", height: "16", rx: "1" }),
467
487
  /* @__PURE__ */ jsx("path", { d: "M14 4v16" }),
@@ -614,19 +634,19 @@ const defaultFindLabels = {
614
634
  invalidRegex: "Invalid pattern",
615
635
  readOnly: "Read-only"
616
636
  };
617
- const bar = "_bar_fzqxj_3";
618
- const row = "_row_fzqxj_25";
619
- const field = "_field_fzqxj_33";
620
- const fieldIcon = "_fieldIcon_fzqxj_49";
621
- const input = "_input_fzqxj_54";
622
- const counter = "_counter_fzqxj_65";
623
- const counterInvalid = "_counterInvalid_fzqxj_74";
624
- const btn$1 = "_btn_fzqxj_78";
625
- const toggle = "_toggle_fzqxj_106";
626
- const toggleOn = "_toggleOn_fzqxj_111";
627
- const textBtn = "_textBtn_fzqxj_121";
628
- const spacer = "_spacer_fzqxj_126";
629
- const readOnly = "_readOnly_fzqxj_131";
637
+ const bar = "_bar_1h61e_3";
638
+ const row = "_row_1h61e_25";
639
+ const field = "_field_1h61e_43";
640
+ const fieldIcon = "_fieldIcon_1h61e_62";
641
+ const input = "_input_1h61e_67";
642
+ const counter = "_counter_1h61e_79";
643
+ const counterInvalid = "_counterInvalid_1h61e_89";
644
+ const btn$1 = "_btn_1h61e_93";
645
+ const toggle = "_toggle_1h61e_29";
646
+ const toggleOn = "_toggleOn_1h61e_135";
647
+ const iconGroup = "_iconGroup_1h61e_29";
648
+ const spacer = "_spacer_1h61e_150";
649
+ const readOnly = "_readOnly_1h61e_155";
630
650
  const styles$5 = {
631
651
  bar,
632
652
  row,
@@ -638,7 +658,7 @@ const styles$5 = {
638
658
  btn: btn$1,
639
659
  toggle,
640
660
  toggleOn,
641
- textBtn,
661
+ iconGroup,
642
662
  spacer,
643
663
  readOnly
644
664
  };
@@ -647,11 +667,20 @@ function FindReplaceBar({
647
667
  onClose,
648
668
  labels,
649
669
  inputRef,
650
- className
670
+ className,
671
+ style
651
672
  }) {
652
673
  const t = { ...defaultFindLabels, ...labels };
653
674
  const [term, setTerm] = useState("");
654
675
  const [replaceTerm, setReplaceTerm] = useState("");
676
+ const hasExtension = typeof editor.commands.setSearchTerm === "function";
677
+ useEffect(() => {
678
+ if (!hasExtension) {
679
+ console.warn(
680
+ "[tiptap-markdown-react] FindReplaceBar 需要官方 find 扩展:请让 <MarkdownWysiwygEditor findReplace> 保持开启(默认 true),否则 setSearchTerm / replaceAll 等命令不存在。"
681
+ );
682
+ }
683
+ }, [hasExtension]);
655
684
  const state = useEditorState({
656
685
  editor,
657
686
  selector: ({ editor: instance }) => {
@@ -665,13 +694,20 @@ function FindReplaceBar({
665
694
  };
666
695
  }
667
696
  });
697
+ const runCommand = useCallback(
698
+ (run) => {
699
+ if (!hasExtension) return;
700
+ runFindCommand(run);
701
+ },
702
+ [hasExtension]
703
+ );
668
704
  const appliedTermRef = useRef(null);
669
705
  const pushTerm = useCallback(
670
706
  (value) => {
671
707
  appliedTermRef.current = value;
672
- runFindCommand(() => editor.commands.setSearchTerm(value));
708
+ runCommand(() => editor.commands.setSearchTerm(value));
673
709
  },
674
- [editor]
710
+ [editor, runCommand]
675
711
  );
676
712
  const flushTerm = useCallback(() => {
677
713
  if (appliedTermRef.current !== term) pushTerm(term);
@@ -682,19 +718,19 @@ function FindReplaceBar({
682
718
  return () => clearTimeout(timer);
683
719
  }, [term, pushTerm]);
684
720
  useEffect(() => {
685
- runFindCommand(() => editor.commands.setReplaceTerm(replaceTerm));
686
- }, [editor, replaceTerm]);
721
+ runCommand(() => editor.commands.setReplaceTerm(replaceTerm));
722
+ }, [editor, replaceTerm, runCommand]);
687
723
  useEffect(() => {
688
724
  return () => {
689
- if (!editor.isDestroyed) editor.commands.clearSearch();
725
+ if (!editor.isDestroyed) runCommand(() => editor.commands.clearSearch());
690
726
  };
691
- }, [editor]);
727
+ }, [editor, runCommand]);
692
728
  const runAction = useCallback(
693
729
  (action) => {
694
730
  flushTerm();
695
- runFindCommand(action);
731
+ runCommand(action);
696
732
  },
697
- [flushTerm]
733
+ [flushTerm, runCommand]
698
734
  );
699
735
  const invalidPattern = useMemo(
700
736
  () => term !== "" && state.useRegex && createSearchRegex(term, {
@@ -725,17 +761,18 @@ function FindReplaceBar({
725
761
  }
726
762
  };
727
763
  const toggle2 = (key, value) => {
728
- runFindCommand(() => {
764
+ runCommand(() => {
729
765
  if (key === "caseSensitive") editor.commands.setCaseSensitive(value);
730
- else if (key === "wholeWord") editor.commands.setWholeWord(value);
731
- else editor.commands.setUseRegex(value);
766
+ else editor.commands.setWholeWord(value);
732
767
  });
733
768
  };
769
+ if (!hasExtension) return null;
734
770
  const toggleClass = (on) => `${styles$5.btn} ${styles$5.toggle}${on ? ` ${styles$5.toggleOn}` : ""}`;
735
771
  return /* @__PURE__ */ jsxs(
736
772
  "div",
737
773
  {
738
774
  className: className ? `${styles$5.bar} ${className}` : styles$5.bar,
775
+ style,
739
776
  role: "dialog",
740
777
  "aria-label": t.find,
741
778
  onKeyDown: (e2) => {
@@ -761,68 +798,17 @@ function FindReplaceBar({
761
798
  autoFocus: true,
762
799
  spellCheck: false
763
800
  }
801
+ ),
802
+ /* @__PURE__ */ jsx(
803
+ "span",
804
+ {
805
+ className: `${styles$5.counter}${invalidPattern ? ` ${styles$5.counterInvalid}` : ""}`,
806
+ "aria-live": "polite",
807
+ title: invalidPattern ? t.invalidRegex : void 0,
808
+ children: invalidPattern ? t.invalidRegex : counter2
809
+ }
764
810
  )
765
811
  ] }),
766
- /* @__PURE__ */ jsx(
767
- "span",
768
- {
769
- className: `${styles$5.counter}${invalidPattern ? ` ${styles$5.counterInvalid}` : ""}`,
770
- "aria-live": "polite",
771
- title: invalidPattern ? t.invalidRegex : void 0,
772
- children: invalidPattern ? t.invalidRegex : counter2
773
- }
774
- ),
775
- /* @__PURE__ */ jsx(
776
- "button",
777
- {
778
- type: "button",
779
- className: styles$5.btn,
780
- title: t.previous,
781
- "aria-label": t.previous,
782
- disabled: state.total === 0,
783
- onMouseDown: keepFocus,
784
- onClick: () => runAction(() => editor.commands.goToPreviousResult()),
785
- children: /* @__PURE__ */ jsx(ChevronUpIcon, { size: 16 })
786
- }
787
- ),
788
- /* @__PURE__ */ jsx(
789
- "button",
790
- {
791
- type: "button",
792
- className: styles$5.btn,
793
- title: t.next,
794
- "aria-label": t.next,
795
- disabled: state.total === 0,
796
- onMouseDown: keepFocus,
797
- onClick: () => runAction(() => editor.commands.goToNextResult()),
798
- children: /* @__PURE__ */ jsx(ChevronDownIcon, { size: 16 })
799
- }
800
- ),
801
- /* @__PURE__ */ jsx(
802
- "button",
803
- {
804
- type: "button",
805
- className: styles$5.btn,
806
- title: t.close,
807
- "aria-label": t.close,
808
- onClick: onClose,
809
- children: /* @__PURE__ */ jsx(XIcon, { size: 16 })
810
- }
811
- )
812
- ] }),
813
- editor.isEditable ? /* @__PURE__ */ jsxs("div", { className: styles$5.row, children: [
814
- /* @__PURE__ */ jsx("span", { className: styles$5.field, children: /* @__PURE__ */ jsx(
815
- "input",
816
- {
817
- className: styles$5.input,
818
- value: replaceTerm,
819
- onChange: (e2) => setReplaceTerm(e2.target.value),
820
- onKeyDown: onReplaceKeyDown,
821
- placeholder: t.replace,
822
- "aria-label": t.replace,
823
- spellCheck: false
824
- }
825
- ) }),
826
812
  /* @__PURE__ */ jsx(
827
813
  "button",
828
814
  {
@@ -849,40 +835,85 @@ function FindReplaceBar({
849
835
  children: "ab"
850
836
  }
851
837
  ),
852
- /* @__PURE__ */ jsx(
853
- "button",
838
+ /* @__PURE__ */ jsx("span", { className: styles$5.spacer }),
839
+ /* @__PURE__ */ jsxs("span", { className: styles$5.iconGroup, children: [
840
+ /* @__PURE__ */ jsx(
841
+ "button",
842
+ {
843
+ type: "button",
844
+ className: styles$5.btn,
845
+ title: t.previous,
846
+ "aria-label": t.previous,
847
+ disabled: state.total === 0,
848
+ onMouseDown: keepFocus,
849
+ onClick: () => runAction(() => editor.commands.goToPreviousResult()),
850
+ children: /* @__PURE__ */ jsx(ChevronUpIcon, { size: 16 })
851
+ }
852
+ ),
853
+ /* @__PURE__ */ jsx(
854
+ "button",
855
+ {
856
+ type: "button",
857
+ className: styles$5.btn,
858
+ title: t.next,
859
+ "aria-label": t.next,
860
+ disabled: state.total === 0,
861
+ onMouseDown: keepFocus,
862
+ onClick: () => runAction(() => editor.commands.goToNextResult()),
863
+ children: /* @__PURE__ */ jsx(ChevronDownIcon, { size: 16 })
864
+ }
865
+ ),
866
+ /* @__PURE__ */ jsx(
867
+ "button",
868
+ {
869
+ type: "button",
870
+ className: styles$5.btn,
871
+ title: t.close,
872
+ "aria-label": t.close,
873
+ onClick: onClose,
874
+ children: /* @__PURE__ */ jsx(XIcon, { size: 16 })
875
+ }
876
+ )
877
+ ] })
878
+ ] }),
879
+ editor.isEditable ? /* @__PURE__ */ jsxs("div", { className: styles$5.row, children: [
880
+ /* @__PURE__ */ jsx("span", { className: styles$5.field, children: /* @__PURE__ */ jsx(
881
+ "input",
854
882
  {
855
- type: "button",
856
- className: toggleClass(state.useRegex),
857
- title: t.useRegex,
858
- "aria-label": t.useRegex,
859
- "aria-pressed": state.useRegex,
860
- onMouseDown: keepFocus,
861
- onClick: () => toggle2("useRegex", !state.useRegex),
862
- children: ".*"
883
+ className: styles$5.input,
884
+ value: replaceTerm,
885
+ onChange: (e2) => setReplaceTerm(e2.target.value),
886
+ onKeyDown: onReplaceKeyDown,
887
+ placeholder: t.replace,
888
+ "aria-label": t.replace,
889
+ spellCheck: false
863
890
  }
864
- ),
891
+ ) }),
865
892
  /* @__PURE__ */ jsx("span", { className: styles$5.spacer }),
866
893
  /* @__PURE__ */ jsx(
867
894
  "button",
868
895
  {
869
896
  type: "button",
870
- className: `${styles$5.btn} ${styles$5.textBtn}`,
897
+ className: styles$5.btn,
898
+ title: t.replaceOne,
899
+ "aria-label": t.replaceOne,
871
900
  disabled: state.total === 0,
872
901
  onMouseDown: keepFocus,
873
902
  onClick: () => runAction(() => editor.commands.replace()),
874
- children: t.replaceOne
903
+ children: /* @__PURE__ */ jsx(ReplaceIcon, { size: 16 })
875
904
  }
876
905
  ),
877
906
  /* @__PURE__ */ jsx(
878
907
  "button",
879
908
  {
880
909
  type: "button",
881
- className: `${styles$5.btn} ${styles$5.textBtn}`,
910
+ className: styles$5.btn,
911
+ title: t.replaceAll,
912
+ "aria-label": t.replaceAll,
882
913
  disabled: state.total === 0,
883
914
  onMouseDown: keepFocus,
884
915
  onClick: () => runAction(() => editor.commands.replaceAll()),
885
- children: t.replaceAll
916
+ children: /* @__PURE__ */ jsx(ReplaceAllIcon, { size: 16 })
886
917
  }
887
918
  )
888
919
  ] }) : /* @__PURE__ */ jsx("div", { className: styles$5.row, children: /* @__PURE__ */ jsx("span", { className: styles$5.readOnly, children: t.readOnly }) })
@@ -1425,6 +1456,17 @@ const ImageWithConfirmDelete = Image.extend({
1425
1456
  };
1426
1457
  }
1427
1458
  });
1459
+ const DEFAULT_FIND_BAR_OFFSET = { top: 4, right: 4 };
1460
+ function findBarOffsetStyle(offset) {
1461
+ const px = (v) => typeof v === "number" ? `${v}px` : v;
1462
+ return {
1463
+ position: "absolute",
1464
+ top: px(offset.top),
1465
+ right: px(offset.right),
1466
+ bottom: px(offset.bottom),
1467
+ left: px(offset.left)
1468
+ };
1469
+ }
1428
1470
  const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
1429
1471
  initialMarkdown = "",
1430
1472
  editable = true,
@@ -1448,6 +1490,9 @@ const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
1448
1490
  onAnchorClick,
1449
1491
  onSelectionChange,
1450
1492
  findReplace = true,
1493
+ findBar = findReplace,
1494
+ findBarContainer,
1495
+ findBarOffset = DEFAULT_FIND_BAR_OFFSET,
1451
1496
  findShortcut = true,
1452
1497
  findLabels
1453
1498
  }, ref) {
@@ -1513,7 +1558,7 @@ const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
1513
1558
  editor == null ? void 0 : editor.commands.focus();
1514
1559
  }, [editor]);
1515
1560
  useEffect(() => {
1516
- if (!editor || !findReplace || !findShortcut) return;
1561
+ if (!editor || !findReplace || !findBar || !findShortcut) return;
1517
1562
  const onKeyDown = (event) => {
1518
1563
  if (!(event.metaKey || event.ctrlKey) || event.altKey || event.shiftKey) {
1519
1564
  return;
@@ -1535,7 +1580,7 @@ const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
1535
1580
  };
1536
1581
  document.addEventListener("keydown", onKeyDown, true);
1537
1582
  return () => document.removeEventListener("keydown", onKeyDown, true);
1538
- }, [editor, findReplace, findShortcut]);
1583
+ }, [editor, findReplace, findBar, findShortcut]);
1539
1584
  const commentsSignatureRef = useRef("");
1540
1585
  useEffect(() => {
1541
1586
  if (!editor || !editable) return;
@@ -1648,17 +1693,27 @@ const MarkdownWysiwygEditor = forwardRef(function MarkdownWysiwygEditor2({
1648
1693
  }),
1649
1694
  [editor, closeFind]
1650
1695
  );
1696
+ const findBarTarget = typeof findBarContainer === "function" ? findBarContainer() : findBarContainer ?? null;
1697
+ useEffect(() => {
1698
+ if (!findBarTarget) return;
1699
+ if (getComputedStyle(findBarTarget).position === "static") {
1700
+ findBarTarget.style.position = "relative";
1701
+ }
1702
+ }, [findBarTarget]);
1703
+ const findBarNode = editor && findBar && findOpen ? /* @__PURE__ */ jsx(
1704
+ FindReplaceBar,
1705
+ {
1706
+ editor,
1707
+ labels: findLabels,
1708
+ onClose: closeFind,
1709
+ inputRef: findInputRef,
1710
+ className: styles$6.findBar,
1711
+ style: findBarOffsetStyle(findBarOffset)
1712
+ }
1713
+ ) : null;
1651
1714
  return /* @__PURE__ */ jsxs("div", { className: styles$6.editorHost, children: [
1652
- editor && findReplace && findOpen ? /* @__PURE__ */ jsx("div", { className: styles$6.findBarAnchor, children: /* @__PURE__ */ jsx(
1653
- FindReplaceBar,
1654
- {
1655
- editor,
1656
- labels: findLabels,
1657
- onClose: closeFind,
1658
- inputRef: findInputRef,
1659
- className: styles$6.findBar
1660
- }
1661
- ) }) : null,
1715
+ findBarNode && !findBarTarget ? /* @__PURE__ */ jsx("div", { className: styles$6.findBarAnchor, children: findBarNode }) : null,
1716
+ findBarNode && findBarTarget ? createPortal(findBarNode, findBarTarget) : null,
1662
1717
  /* @__PURE__ */ jsx(
1663
1718
  EditorContent,
1664
1719
  {
@@ -3625,6 +3680,8 @@ export {
3625
3680
  MenuIcon,
3626
3681
  PENDING_ANCHOR_CLASS,
3627
3682
  RedoIcon,
3683
+ ReplaceAllIcon,
3684
+ ReplaceIcon,
3628
3685
  R2 as ReportContent,
3629
3686
  R as ReportContentInteractive,
3630
3687
  b as ReportContentWithCharts,