@cyberyozh/text-editor 0.2.2 → 0.3.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/editor.mjs CHANGED
@@ -1,7 +1,7 @@
1
1
  // src/editor/editor.tsx
2
2
  import { useState as useState13, useEffect as useEffect11 } from "react";
3
3
  import { NodeSelection } from "@tiptap/pm/state";
4
- import { Slice as Slice2 } from "@tiptap/pm/model";
4
+ import { Slice as Slice3 } from "@tiptap/pm/model";
5
5
  import { useEditor, EditorContent } from "@tiptap/react";
6
6
  import { BubbleMenu } from "@tiptap/react/menus";
7
7
  import "highlight.js/styles/github-dark.css";
@@ -6751,6 +6751,9 @@ var createHandleKatexAdd = (editor, closeDialogCommand, savedPos) => {
6751
6751
  // src/editor/handlers/insertion-handlers.ts
6752
6752
  import { useEffect as useEffect10, useState as useState12 } from "react";
6753
6753
 
6754
+ // src/editor/handlers/markup-insertion.ts
6755
+ import { Fragment as Fragment4, Slice as Slice2 } from "@tiptap/pm/model";
6756
+
6754
6757
  // src/utils/prosemirror-iterator.ts
6755
6758
  import { Fragment as Fragment3, Slice } from "@tiptap/pm/model";
6756
6759
  function prosemirrorIterator(slice, cb) {
@@ -6791,6 +6794,34 @@ function collectRehostableImages(slice) {
6791
6794
  });
6792
6795
  return imagesToNodes;
6793
6796
  }
6797
+ function removeImagesFromFragment(fragment) {
6798
+ const newNodes = [];
6799
+ fragment.forEach((node) => {
6800
+ if (node.type.name === "image" && !node.attrs.fileId) return;
6801
+ newNodes.push(node.childCount > 0 ? node.copy(removeImagesFromFragment(node.content)) : node);
6802
+ });
6803
+ return Fragment4.from(newNodes);
6804
+ }
6805
+ function validOpenDepth(fragment, requestedDepth, fromEnd = false) {
6806
+ let depth = 0;
6807
+ let current = fragment;
6808
+ while (depth < requestedDepth) {
6809
+ if (current.childCount === 0) break;
6810
+ const node = fromEnd ? current.lastChild : current.firstChild;
6811
+ if (node.isLeaf) break;
6812
+ current = node.content;
6813
+ depth++;
6814
+ }
6815
+ return depth;
6816
+ }
6817
+ function removeImagesFromSlice(slice) {
6818
+ const newContent = removeImagesFromFragment(slice.content);
6819
+ return new Slice2(
6820
+ newContent,
6821
+ validOpenDepth(newContent, slice.openStart),
6822
+ validOpenDepth(newContent, slice.openEnd, true)
6823
+ );
6824
+ }
6794
6825
  function applyUploadResultsToNodes(imagesToNodes, results) {
6795
6826
  results.forEach((result, index) => {
6796
6827
  if (!result) return;
@@ -6803,7 +6834,7 @@ function applyUploadResultsToNodes(imagesToNodes, results) {
6803
6834
  }
6804
6835
 
6805
6836
  // src/editor/handlers/insertion-handlers.ts
6806
- function useInsertionHandlers() {
6837
+ function useInsertionHandlers(imageHandlers) {
6807
6838
  const [insertedImage, setInsertedImage] = useState12(null);
6808
6839
  const { activeDialog, openDialogCommand } = useDialogCommand();
6809
6840
  useEffect10(() => {
@@ -6815,6 +6846,7 @@ function useInsertionHandlers() {
6815
6846
  if (!file || !file.type.startsWith("image/")) return;
6816
6847
  event.preventDefault();
6817
6848
  event.stopPropagation();
6849
+ if (!imageHandlers?.upload) return;
6818
6850
  setInsertedImage(file);
6819
6851
  openDialogCommand("image");
6820
6852
  }
@@ -6826,8 +6858,7 @@ function useInsertionHandlers() {
6826
6858
  const file = event.dataTransfer?.files?.[0];
6827
6859
  genericInsertionHandler(file, event);
6828
6860
  }
6829
- function onMarkupInsertion(view, event, slice, setDisabled, uploadMultipleByURL) {
6830
- if (!uploadMultipleByURL) return;
6861
+ function onMarkupInsertion(view, event, slice, setDisabled) {
6831
6862
  let hasMarkupInsertion = false;
6832
6863
  if ("clipboardData" in event && Array.from(event.clipboardData?.items ?? []).some(
6833
6864
  (item) => item.type === "text/html"
@@ -6840,14 +6871,18 @@ function useInsertionHandlers() {
6840
6871
  hasMarkupInsertion = true;
6841
6872
  }
6842
6873
  if (hasMarkupInsertion) {
6843
- const imagesToNodes = collectRehostableImages(slice);
6844
- setDisabled(true);
6845
- uploadMultipleByURL(imagesToNodes.map(([url]) => url)).then((results) => {
6846
- applyUploadResultsToNodes(imagesToNodes, results);
6847
- view.dispatch(view.state.tr.replaceSelection(slice));
6848
- }).finally(() => {
6849
- setDisabled(false);
6850
- });
6874
+ if (imageHandlers?.uploadMultipleByURL) {
6875
+ setDisabled(true);
6876
+ const imagesToNodes = collectRehostableImages(slice);
6877
+ imageHandlers.uploadMultipleByURL(imagesToNodes.map(([url]) => url)).then((results) => {
6878
+ applyUploadResultsToNodes(imagesToNodes, results);
6879
+ view.dispatch(view.state.tr.replaceSelection(slice));
6880
+ }).finally(() => {
6881
+ setDisabled(false);
6882
+ });
6883
+ } else {
6884
+ view.dispatch(view.state.tr.replaceSelection(removeImagesFromSlice(slice)));
6885
+ }
6851
6886
  return true;
6852
6887
  }
6853
6888
  }
@@ -7608,7 +7643,7 @@ function getTranslations(lang) {
7608
7643
  }
7609
7644
 
7610
7645
  // src/editor/editor.tsx
7611
- import { Fragment as Fragment4, jsx as jsx92, jsxs as jsxs35 } from "react/jsx-runtime";
7646
+ import { Fragment as Fragment5, jsx as jsx92, jsxs as jsxs35 } from "react/jsx-runtime";
7612
7647
  function TiptapContent({
7613
7648
  content,
7614
7649
  handleChange,
@@ -7642,7 +7677,7 @@ function TiptapContent({
7642
7677
  onPaste,
7643
7678
  onDrop,
7644
7679
  onMarkupInsertion
7645
- } = useInsertionHandlers();
7680
+ } = useInsertionHandlers(imageHandlers);
7646
7681
  const editor = useEditor(
7647
7682
  {
7648
7683
  editable: isEditable && !disabled,
@@ -7673,8 +7708,7 @@ function TiptapContent({
7673
7708
  view,
7674
7709
  event,
7675
7710
  slice,
7676
- setIsDisabledInternal,
7677
- imageHandlers?.uploadMultipleByURL
7711
+ setIsDisabledInternal
7678
7712
  );
7679
7713
  if (typeof toReturn === "boolean") return toReturn;
7680
7714
  return false;
@@ -7684,8 +7718,7 @@ function TiptapContent({
7684
7718
  view,
7685
7719
  event,
7686
7720
  slice,
7687
- setIsDisabledInternal,
7688
- imageHandlers?.uploadMultipleByURL
7721
+ setIsDisabledInternal
7689
7722
  );
7690
7723
  if (typeof toReturn === "boolean") return toReturn;
7691
7724
  try {
@@ -7694,7 +7727,7 @@ function TiptapContent({
7694
7727
  const json = JSON.parse(text);
7695
7728
  if (json.type === "doc" && json.content) {
7696
7729
  const node = view.state.schema.nodeFromJSON(json);
7697
- const newSlice = new Slice2(node.content, 0, 0);
7730
+ const newSlice = new Slice3(node.content, 0, 0);
7698
7731
  view.dispatch(view.state.tr.replaceSelection(newSlice));
7699
7732
  return true;
7700
7733
  }
@@ -7757,7 +7790,7 @@ function TiptapContent({
7757
7790
  return true;
7758
7791
  };
7759
7792
  if (!editor) return null;
7760
- return /* @__PURE__ */ jsxs35(Fragment4, { children: [
7793
+ return /* @__PURE__ */ jsxs35(Fragment5, { children: [
7761
7794
  /* @__PURE__ */ jsx92(DragHandle, { editor }),
7762
7795
  isEditable && !disabled && /* @__PURE__ */ jsx92(TableMenu, { editor }),
7763
7796
  isEditable && !disabled && /* @__PURE__ */ jsx92(
@@ -7786,7 +7819,7 @@ function TiptapContent({
7786
7819
  }
7787
7820
  ),
7788
7821
  !!error && /* @__PURE__ */ jsx92("p", { className: "tiptap-error-message", children: error }),
7789
- isEditable && /* @__PURE__ */ jsxs35(Fragment4, { children: [
7822
+ isEditable && /* @__PURE__ */ jsxs35(Fragment5, { children: [
7790
7823
  activeDialog === "image" && /* @__PURE__ */ jsx92(
7791
7824
  ImageDialog,
7792
7825
  {