markdown-wysiwyg-editor 0.2.5 → 0.2.8

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
@@ -1560,7 +1560,7 @@ https://github.com/highlightjs/highlight.js/issues/2277`);
1560
1560
  // src/components/MarkdownEditor.tsx
1561
1561
  import React8, { useState as useState15, useCallback as useCallback4, useEffect as useEffect14 } from "react";
1562
1562
 
1563
- // node_modules/.bun/@tiptap+react@3.14.0+6d8c22b45e24b890/node_modules/@tiptap/react/dist/index.js
1563
+ // node_modules/.bun/@tiptap+react@3.15.3+2bbf2f46acd5f4b8/node_modules/@tiptap/react/dist/index.js
1564
1564
  var import_shim = __toESM(require_shim(), 1);
1565
1565
  import { createContext, useContext, useMemo } from "react";
1566
1566
  import React3, { forwardRef } from "react";
@@ -12081,7 +12081,7 @@ function keydownHandler(bindings) {
12081
12081
  return false;
12082
12082
  };
12083
12083
  }
12084
- // node_modules/.bun/@tiptap+core@3.14.0+da8d1d9e70484869/node_modules/@tiptap/core/dist/index.js
12084
+ // node_modules/.bun/@tiptap+core@3.15.3+2552a9caaf6753d4/node_modules/@tiptap/core/dist/index.js
12085
12085
  var __defProp2 = Object.defineProperty;
12086
12086
  var __export = (target, all) => {
12087
12087
  for (var name in all)
@@ -12519,6 +12519,9 @@ function isAndroid() {
12519
12519
  function isiOS() {
12520
12520
  return ["iPad Simulator", "iPhone Simulator", "iPod Simulator", "iPad", "iPhone", "iPod"].includes(navigator.platform) || navigator.userAgent.includes("Mac") && "ontouchend" in document;
12521
12521
  }
12522
+ function isSafari() {
12523
+ return typeof navigator !== "undefined" ? /^((?!chrome|android).)*safari/i.test(navigator.userAgent) : false;
12524
+ }
12522
12525
  var focus = (position = null, options = {}) => ({ editor, view, tr, dispatch }) => {
12523
12526
  options = {
12524
12527
  scrollIntoView: true,
@@ -12528,6 +12531,9 @@ var focus = (position = null, options = {}) => ({ editor, view, tr, dispatch })
12528
12531
  if (isiOS() || isAndroid()) {
12529
12532
  view.dom.focus();
12530
12533
  }
12534
+ if (isSafari() && !isiOS() && !isAndroid()) {
12535
+ view.dom.focus({ preventScroll: true });
12536
+ }
12531
12537
  requestAnimationFrame(() => {
12532
12538
  if (!editor.isDestroyed) {
12533
12539
  view.focus();
@@ -15095,6 +15101,26 @@ var ExtensionManager = class {
15095
15101
  return [extension.name, nodeview];
15096
15102
  }));
15097
15103
  }
15104
+ dispatchTransaction(baseDispatch) {
15105
+ const { editor } = this;
15106
+ const extensions = sortExtensions([...this.extensions].reverse());
15107
+ return extensions.reduceRight((next, extension) => {
15108
+ const context = {
15109
+ name: extension.name,
15110
+ options: extension.options,
15111
+ storage: this.editor.extensionStorage[extension.name],
15112
+ editor,
15113
+ type: getSchemaTypeByName(extension.name, this.schema)
15114
+ };
15115
+ const dispatchTransaction = getExtensionField(extension, "dispatchTransaction", context);
15116
+ if (!dispatchTransaction) {
15117
+ return next;
15118
+ }
15119
+ return (transaction) => {
15120
+ dispatchTransaction.call(context, { transaction, next });
15121
+ };
15122
+ }, baseDispatch);
15123
+ }
15098
15124
  get markViews() {
15099
15125
  const { editor } = this;
15100
15126
  const { markExtensions } = splitExtensions(this.extensions);
@@ -15883,7 +15909,8 @@ var Editor = class extends EventEmitter {
15883
15909
  },
15884
15910
  onPaste: () => null,
15885
15911
  onDrop: () => null,
15886
- onDelete: () => null
15912
+ onDelete: () => null,
15913
+ enableExtensionDispatchTransaction: true
15887
15914
  };
15888
15915
  this.isCapturingTransaction = false;
15889
15916
  this.capturedTransaction = null;
@@ -16130,14 +16157,16 @@ var Editor = class extends EventEmitter {
16130
16157
  return doc3;
16131
16158
  }
16132
16159
  createView(element) {
16133
- var _a;
16160
+ const { editorProps, enableExtensionDispatchTransaction } = this.options;
16161
+ const baseDispatch = editorProps.dispatchTransaction || this.dispatchTransaction.bind(this);
16162
+ const dispatch = enableExtensionDispatchTransaction ? this.extensionManager.dispatchTransaction(baseDispatch) : baseDispatch;
16134
16163
  this.editorView = new EditorView(element, {
16135
- ...this.options.editorProps,
16164
+ ...editorProps,
16136
16165
  attributes: {
16137
16166
  role: "textbox",
16138
- ...(_a = this.options.editorProps) == null ? undefined : _a.attributes
16167
+ ...editorProps == null ? undefined : editorProps.attributes
16139
16168
  },
16140
- dispatchTransaction: this.dispatchTransaction.bind(this),
16169
+ dispatchTransaction: dispatch,
16141
16170
  state: this.editorState,
16142
16171
  markViews: this.extensionManager.markViews,
16143
16172
  nodeViews: this.extensionManager.nodeViews
@@ -17590,7 +17619,7 @@ function markPasteRule(config) {
17590
17619
  });
17591
17620
  }
17592
17621
 
17593
- // node_modules/.bun/@tiptap+react@3.14.0+6d8c22b45e24b890/node_modules/@tiptap/react/dist/index.js
17622
+ // node_modules/.bun/@tiptap+react@3.15.3+2bbf2f46acd5f4b8/node_modules/@tiptap/react/dist/index.js
17594
17623
  var import_shim2 = __toESM(require_shim(), 1);
17595
17624
  import { useDebugValue as useDebugValue2, useEffect as useEffect2, useRef, useState as useState2 } from "react";
17596
17625
 
@@ -18029,7 +18058,7 @@ function createCustomEqual(options = {}) {
18029
18058
  return createIsEqual({ circular, comparator, createState, equals, strict });
18030
18059
  }
18031
18060
 
18032
- // node_modules/.bun/@tiptap+react@3.14.0+6d8c22b45e24b890/node_modules/@tiptap/react/dist/index.js
18061
+ // node_modules/.bun/@tiptap+react@3.15.3+2bbf2f46acd5f4b8/node_modules/@tiptap/react/dist/index.js
18033
18062
  var import_with_selector = __toESM(require_with_selector(), 1);
18034
18063
  import { useDebugValue, useEffect, useLayoutEffect, useState } from "react";
18035
18064
  import { jsx as jsx2, jsxs as jsxs2 } from "react/jsx-runtime";
@@ -18540,6 +18569,7 @@ function isReact19Plus() {
18540
18569
  var ReactRenderer = class {
18541
18570
  constructor(component, { editor, props = {}, as = "div", className = "" }) {
18542
18571
  this.ref = null;
18572
+ this.destroyed = false;
18543
18573
  this.id = Math.floor(Math.random() * 4294967295).toString();
18544
18574
  this.component = component;
18545
18575
  this.editor = editor;
@@ -18555,12 +18585,18 @@ var ReactRenderer = class {
18555
18585
  });
18556
18586
  } else {
18557
18587
  queueMicrotask(() => {
18588
+ if (this.destroyed) {
18589
+ return;
18590
+ }
18558
18591
  this.render();
18559
18592
  });
18560
18593
  }
18561
18594
  }
18562
18595
  render() {
18563
18596
  var _a;
18597
+ if (this.destroyed) {
18598
+ return;
18599
+ }
18564
18600
  const Component = this.component;
18565
18601
  const props = this.props;
18566
18602
  const editor = this.editor;
@@ -18579,6 +18615,9 @@ var ReactRenderer = class {
18579
18615
  (_a = editor == null ? undefined : editor.contentComponent) == null || _a.setRenderer(this.id, this);
18580
18616
  }
18581
18617
  updateProps(props = {}) {
18618
+ if (this.destroyed) {
18619
+ return;
18620
+ }
18582
18621
  this.props = {
18583
18622
  ...this.props,
18584
18623
  ...props
@@ -18587,6 +18626,7 @@ var ReactRenderer = class {
18587
18626
  }
18588
18627
  destroy() {
18589
18628
  var _a;
18629
+ this.destroyed = true;
18590
18630
  const editor = this.editor;
18591
18631
  (_a = editor == null ? undefined : editor.contentComponent) == null || _a.removeRenderer(this.id);
18592
18632
  try {
@@ -19761,7 +19801,7 @@ var undo = buildCommand(false, true);
19761
19801
  var redo = buildCommand(true, true);
19762
19802
  var undoNoScroll = buildCommand(false, false);
19763
19803
  var redoNoScroll = buildCommand(true, false);
19764
- // node_modules/.bun/@tiptap+extensions@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extensions/dist/index.js
19804
+ // node_modules/.bun/@tiptap+extensions@3.15.3+aa048d05049272a7/node_modules/@tiptap/extensions/dist/index.js
19765
19805
  var CharacterCount = Extension.create({
19766
19806
  name: "characterCount",
19767
19807
  addOptions() {
@@ -20105,10 +20145,10 @@ var UndoRedo = Extension.create({
20105
20145
  }
20106
20146
  });
20107
20147
 
20108
- // node_modules/.bun/@tiptap+extension-character-count@3.14.0+ea54e60bae9eda84/node_modules/@tiptap/extension-character-count/dist/index.js
20148
+ // node_modules/.bun/@tiptap+extension-character-count@3.15.3+9f9d100532d1ad91/node_modules/@tiptap/extension-character-count/dist/index.js
20109
20149
  var index_default = CharacterCount;
20110
20150
 
20111
- // node_modules/.bun/@tiptap+extension-image@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-image/dist/index.js
20151
+ // node_modules/.bun/@tiptap+extension-image@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-image/dist/index.js
20112
20152
  var inputRegex = /(?:^|\s)(!\[(.+|:?)]\((\S+)(?:(?:\s+)["'](\S+)["'])?\))$/;
20113
20153
  var Image2 = Node3.create({
20114
20154
  name: "image",
@@ -21231,7 +21271,7 @@ function find(str, type = null, opts = null) {
21231
21271
  return filtered;
21232
21272
  }
21233
21273
 
21234
- // node_modules/.bun/@tiptap+extension-link@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-link/dist/index.js
21274
+ // node_modules/.bun/@tiptap+extension-link@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-link/dist/index.js
21235
21275
  var UNICODE_WHITESPACE_PATTERN = "[\x00-   ᠎ -\u2029  ]";
21236
21276
  var UNICODE_WHITESPACE_REGEX = new RegExp(UNICODE_WHITESPACE_PATTERN);
21237
21277
  var UNICODE_WHITESPACE_REGEX_END = new RegExp(`${UNICODE_WHITESPACE_PATTERN}$`);
@@ -21375,7 +21415,7 @@ function pasteHandler(options) {
21375
21415
  textContent += node.textContent;
21376
21416
  });
21377
21417
  const link = find(textContent, { defaultProtocol: options.defaultProtocol }).find((item) => item.isLink && item.value === textContent);
21378
- if (!textContent || !link || shouldAutoLink !== undefined && !shouldAutoLink(link.href)) {
21418
+ if (!textContent || !link || shouldAutoLink !== undefined && !shouldAutoLink(link.value)) {
21379
21419
  return false;
21380
21420
  }
21381
21421
  return options.editor.commands.setMark(options.type, {
@@ -21436,7 +21476,22 @@ var Link = Mark2.create({
21436
21476
  },
21437
21477
  isAllowedUri: (url, ctx) => !!isAllowedUri(url, ctx.protocols),
21438
21478
  validate: (url) => !!url,
21439
- shouldAutoLink: (url) => !!url
21479
+ shouldAutoLink: (url) => {
21480
+ const hasProtocol = /^[a-z][a-z0-9+.-]*:\/\//i.test(url);
21481
+ const hasMaybeProtocol = /^[a-z][a-z0-9+.-]*:/i.test(url);
21482
+ if (hasProtocol || hasMaybeProtocol && !url.includes("@")) {
21483
+ return true;
21484
+ }
21485
+ const urlWithoutUserinfo = url.includes("@") ? url.split("@").pop() : url;
21486
+ const hostname = urlWithoutUserinfo.split(/[/?#:]/)[0];
21487
+ if (/^\d{1,3}(\.\d{1,3}){3}$/.test(hostname)) {
21488
+ return false;
21489
+ }
21490
+ if (!/\./.test(hostname)) {
21491
+ return false;
21492
+ }
21493
+ return true;
21494
+ }
21440
21495
  };
21441
21496
  },
21442
21497
  addAttributes() {
@@ -23594,7 +23649,7 @@ function tableEditing({ allowTableNodeSelection = false } = {}) {
23594
23649
  }
23595
23650
  });
23596
23651
  }
23597
- // node_modules/.bun/@tiptap+extension-table@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-table/dist/index.js
23652
+ // node_modules/.bun/@tiptap+extension-table@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-table/dist/index.js
23598
23653
  var TableCell = Node3.create({
23599
23654
  name: "tableCell",
23600
23655
  addOptions() {
@@ -24139,16 +24194,16 @@ var TableKit = Extension.create({
24139
24194
  }
24140
24195
  });
24141
24196
 
24142
- // node_modules/.bun/@tiptap+extension-table-cell@3.14.0+fbcaf6fb0f41e891/node_modules/@tiptap/extension-table-cell/dist/index.js
24197
+ // node_modules/.bun/@tiptap+extension-table-cell@3.15.3+a85e1fcc83d8b887/node_modules/@tiptap/extension-table-cell/dist/index.js
24143
24198
  var index_default4 = TableCell;
24144
24199
 
24145
- // node_modules/.bun/@tiptap+extension-table-header@3.14.0+fbcaf6fb0f41e891/node_modules/@tiptap/extension-table-header/dist/index.js
24200
+ // node_modules/.bun/@tiptap+extension-table-header@3.15.3+a85e1fcc83d8b887/node_modules/@tiptap/extension-table-header/dist/index.js
24146
24201
  var index_default5 = TableHeader;
24147
24202
 
24148
- // node_modules/.bun/@tiptap+extension-table-row@3.14.0+fbcaf6fb0f41e891/node_modules/@tiptap/extension-table-row/dist/index.js
24203
+ // node_modules/.bun/@tiptap+extension-table-row@3.15.3+a85e1fcc83d8b887/node_modules/@tiptap/extension-table-row/dist/index.js
24149
24204
  var index_default6 = TableRow;
24150
24205
 
24151
- // node_modules/.bun/@tiptap+extension-typography@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-typography/dist/index.js
24206
+ // node_modules/.bun/@tiptap+extension-typography@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-typography/dist/index.js
24152
24207
  var emDash = (override) => textInputRule({
24153
24208
  find: /--$/,
24154
24209
  replace: override != null ? override : "—"
@@ -24338,7 +24393,7 @@ var Typography = Extension.create({
24338
24393
  });
24339
24394
  var index_default7 = Typography;
24340
24395
 
24341
- // node_modules/.bun/@tiptap+core@3.14.0+da8d1d9e70484869/node_modules/@tiptap/core/dist/jsx-runtime/jsx-runtime.js
24396
+ // node_modules/.bun/@tiptap+core@3.15.3+2552a9caaf6753d4/node_modules/@tiptap/core/dist/jsx-runtime/jsx-runtime.js
24342
24397
  var h = (tag, attributes) => {
24343
24398
  if (tag === "slot") {
24344
24399
  return 0;
@@ -24353,7 +24408,7 @@ var h = (tag, attributes) => {
24353
24408
  return [tag, rest, children];
24354
24409
  };
24355
24410
 
24356
- // node_modules/.bun/@tiptap+extension-blockquote@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-blockquote/dist/index.js
24411
+ // node_modules/.bun/@tiptap+extension-blockquote@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-blockquote/dist/index.js
24357
24412
  var inputRegex2 = /^\s*>\s$/;
24358
24413
  var Blockquote = Node3.create({
24359
24414
  name: "blockquote",
@@ -24425,7 +24480,7 @@ ${prefix}
24425
24480
  }
24426
24481
  });
24427
24482
 
24428
- // node_modules/.bun/@tiptap+extension-bold@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-bold/dist/index.js
24483
+ // node_modules/.bun/@tiptap+extension-bold@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-bold/dist/index.js
24429
24484
  var starInputRegex = /(?:^|\s)(\*\*(?!\s+\*\*)((?:[^*]+))\*\*(?!\s+\*\*))$/;
24430
24485
  var starPasteRegex = /(?:^|\s)(\*\*(?!\s+\*\*)((?:[^*]+))\*\*(?!\s+\*\*))/g;
24431
24486
  var underscoreInputRegex = /(?:^|\s)(__(?!\s+__)((?:[^_]+))__(?!\s+__))$/;
@@ -24511,7 +24566,7 @@ var Bold = Mark2.create({
24511
24566
  }
24512
24567
  });
24513
24568
 
24514
- // node_modules/.bun/@tiptap+extension-code@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-code/dist/index.js
24569
+ // node_modules/.bun/@tiptap+extension-code@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-code/dist/index.js
24515
24570
  var inputRegex3 = /(^|[^`])`([^`]+)`(?!`)$/;
24516
24571
  var pasteRegex = /(^|[^`])`([^`]+)`(?!`)/g;
24517
24572
  var Code = Mark2.create({
@@ -24576,7 +24631,7 @@ var Code = Mark2.create({
24576
24631
  }
24577
24632
  });
24578
24633
 
24579
- // node_modules/.bun/@tiptap+extension-code-block@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-code-block/dist/index.js
24634
+ // node_modules/.bun/@tiptap+extension-code-block@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-code-block/dist/index.js
24580
24635
  var DEFAULT_TAB_SIZE = 4;
24581
24636
  var backtickInputRegex = /^```([a-z]+)?[\s\n]$/;
24582
24637
  var tildeInputRegex = /^~~~([a-z]+)?[\s\n]$/;
@@ -24892,7 +24947,7 @@ var CodeBlock = Node3.create({
24892
24947
  });
24893
24948
  var index_default8 = CodeBlock;
24894
24949
 
24895
- // node_modules/.bun/@tiptap+extension-document@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-document/dist/index.js
24950
+ // node_modules/.bun/@tiptap+extension-document@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-document/dist/index.js
24896
24951
  var Document = Node3.create({
24897
24952
  name: "doc",
24898
24953
  topNode: true,
@@ -24907,7 +24962,7 @@ var Document = Node3.create({
24907
24962
  }
24908
24963
  });
24909
24964
 
24910
- // node_modules/.bun/@tiptap+extension-hard-break@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-hard-break/dist/index.js
24965
+ // node_modules/.bun/@tiptap+extension-hard-break@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-hard-break/dist/index.js
24911
24966
  var HardBreak = Node3.create({
24912
24967
  name: "hardBreak",
24913
24968
  markdownTokenName: "br",
@@ -24971,7 +25026,7 @@ var HardBreak = Node3.create({
24971
25026
  }
24972
25027
  });
24973
25028
 
24974
- // node_modules/.bun/@tiptap+extension-heading@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-heading/dist/index.js
25029
+ // node_modules/.bun/@tiptap+extension-heading@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-heading/dist/index.js
24975
25030
  var Heading = Node3.create({
24976
25031
  name: "heading",
24977
25032
  addOptions() {
@@ -25051,7 +25106,7 @@ var Heading = Node3.create({
25051
25106
  }
25052
25107
  });
25053
25108
 
25054
- // node_modules/.bun/@tiptap+extension-horizontal-rule@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-horizontal-rule/dist/index.js
25109
+ // node_modules/.bun/@tiptap+extension-horizontal-rule@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-horizontal-rule/dist/index.js
25055
25110
  var HorizontalRule = Node3.create({
25056
25111
  name: "horizontalRule",
25057
25112
  addOptions() {
@@ -25127,7 +25182,7 @@ var HorizontalRule = Node3.create({
25127
25182
  }
25128
25183
  });
25129
25184
 
25130
- // node_modules/.bun/@tiptap+extension-italic@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-italic/dist/index.js
25185
+ // node_modules/.bun/@tiptap+extension-italic@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-italic/dist/index.js
25131
25186
  var starInputRegex2 = /(?:^|\s)(\*(?!\s+\*)((?:[^*]+))\*(?!\s+\*))$/;
25132
25187
  var starPasteRegex2 = /(?:^|\s)(\*(?!\s+\*)((?:[^*]+))\*(?!\s+\*))/g;
25133
25188
  var underscoreInputRegex2 = /(?:^|\s)(_(?!\s+_)((?:[^_]+))_(?!\s+_))$/;
@@ -25212,7 +25267,7 @@ var Italic = Mark2.create({
25212
25267
  }
25213
25268
  });
25214
25269
 
25215
- // node_modules/.bun/@tiptap+extension-list@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-list/dist/index.js
25270
+ // node_modules/.bun/@tiptap+extension-list@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-list/dist/index.js
25216
25271
  var __defProp3 = Object.defineProperty;
25217
25272
  var __export2 = (target, all) => {
25218
25273
  for (var name in all)
@@ -26033,6 +26088,7 @@ var TaskItem = Node3.create({
26033
26088
  Object.entries(HTMLAttributes).forEach(([key, value]) => {
26034
26089
  listItem.setAttribute(key, value);
26035
26090
  });
26091
+ let prevRenderedAttributeKeys = new Set(Object.keys(HTMLAttributes));
26036
26092
  return {
26037
26093
  dom: listItem,
26038
26094
  contentDOM: content,
@@ -26043,6 +26099,31 @@ var TaskItem = Node3.create({
26043
26099
  listItem.dataset.checked = updatedNode.attrs.checked;
26044
26100
  checkbox.checked = updatedNode.attrs.checked;
26045
26101
  updateA11Y(updatedNode);
26102
+ const extensionAttributes = editor.extensionManager.attributes;
26103
+ const newHTMLAttributes = getRenderedAttributes(updatedNode, extensionAttributes);
26104
+ const newKeys = new Set(Object.keys(newHTMLAttributes));
26105
+ const staticAttrs = this.options.HTMLAttributes;
26106
+ prevRenderedAttributeKeys.forEach((key) => {
26107
+ if (!newKeys.has(key)) {
26108
+ if (key in staticAttrs) {
26109
+ listItem.setAttribute(key, staticAttrs[key]);
26110
+ } else {
26111
+ listItem.removeAttribute(key);
26112
+ }
26113
+ }
26114
+ });
26115
+ Object.entries(newHTMLAttributes).forEach(([key, value]) => {
26116
+ if (value === null || value === undefined) {
26117
+ if (key in staticAttrs) {
26118
+ listItem.setAttribute(key, staticAttrs[key]);
26119
+ } else {
26120
+ listItem.removeAttribute(key);
26121
+ }
26122
+ } else {
26123
+ listItem.setAttribute(key, value);
26124
+ }
26125
+ });
26126
+ prevRenderedAttributeKeys = newKeys;
26046
26127
  return true;
26047
26128
  }
26048
26129
  };
@@ -26204,7 +26285,7 @@ var ListKit = Extension.create({
26204
26285
  }
26205
26286
  });
26206
26287
 
26207
- // node_modules/.bun/@tiptap+extension-paragraph@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-paragraph/dist/index.js
26288
+ // node_modules/.bun/@tiptap+extension-paragraph@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-paragraph/dist/index.js
26208
26289
  var Paragraph = Node3.create({
26209
26290
  name: "paragraph",
26210
26291
  priority: 1000,
@@ -26248,7 +26329,7 @@ var Paragraph = Node3.create({
26248
26329
  }
26249
26330
  });
26250
26331
 
26251
- // node_modules/.bun/@tiptap+extension-strike@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-strike/dist/index.js
26332
+ // node_modules/.bun/@tiptap+extension-strike@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-strike/dist/index.js
26252
26333
  var inputRegex5 = /(?:^|\s)(~~(?!\s+~~)((?:[^~]+))~~(?!\s+~~))$/;
26253
26334
  var pasteRegex2 = /(?:^|\s)(~~(?!\s+~~)((?:[^~]+))~~(?!\s+~~))/g;
26254
26335
  var Strike = Mark2.create({
@@ -26322,7 +26403,7 @@ var Strike = Mark2.create({
26322
26403
  }
26323
26404
  });
26324
26405
 
26325
- // node_modules/.bun/@tiptap+extension-text@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-text/dist/index.js
26406
+ // node_modules/.bun/@tiptap+extension-text@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-text/dist/index.js
26326
26407
  var Text2 = Node3.create({
26327
26408
  name: "text",
26328
26409
  group: "inline",
@@ -26335,7 +26416,7 @@ var Text2 = Node3.create({
26335
26416
  renderMarkdown: (node) => node.text || ""
26336
26417
  });
26337
26418
 
26338
- // node_modules/.bun/@tiptap+extension-underline@3.14.0+855f13b920abd4ed/node_modules/@tiptap/extension-underline/dist/index.js
26419
+ // node_modules/.bun/@tiptap+extension-underline@3.15.3+aa048d05049272a7/node_modules/@tiptap/extension-underline/dist/index.js
26339
26420
  var Underline = Mark2.create({
26340
26421
  name: "underline",
26341
26422
  addOptions() {
@@ -26406,7 +26487,7 @@ var Underline = Mark2.create({
26406
26487
  }
26407
26488
  });
26408
26489
 
26409
- // node_modules/.bun/@tiptap+starter-kit@3.14.0/node_modules/@tiptap/starter-kit/dist/index.js
26490
+ // node_modules/.bun/@tiptap+starter-kit@3.15.3/node_modules/@tiptap/starter-kit/dist/index.js
26410
26491
  var StarterKit = Extension.create({
26411
26492
  name: "starterKit",
26412
26493
  addExtensions() {
@@ -38998,6 +39079,9 @@ class HastEmitter {
38998
39079
  return "";
38999
39080
  }
39000
39081
  }
39082
+ // src/hooks/useMarkdownEditor.ts
39083
+ import { useRef as useRef3 } from "react";
39084
+
39001
39085
  // src/converters/JsonToMarkdownConverter.ts
39002
39086
  var log = createLogger("JsonToMarkdownConverter");
39003
39087
 
@@ -39226,7 +39310,7 @@ ${content.trim()}
39226
39310
  }
39227
39311
  var JsonToMarkdownConverter_default = JsonToMarkdownConverter;
39228
39312
 
39229
- // node_modules/.bun/@tiptap+extension-code-block-lowlight@3.14.0+fb0c77bd32b0520e/node_modules/@tiptap/extension-code-block-lowlight/dist/index.js
39313
+ // node_modules/.bun/@tiptap+extension-code-block-lowlight@3.15.3+b67669a1d1743f75/node_modules/@tiptap/extension-code-block-lowlight/dist/index.js
39230
39314
  function parseNodes(nodes, className = []) {
39231
39315
  return nodes.flatMap((node) => {
39232
39316
  const classes = [...className, ...node.properties ? node.properties.className : []];
@@ -40406,37 +40490,63 @@ var createLinkClickExtension = (handleContextMenu) => Extension.create({
40406
40490
  key: new PluginKey("linkClick"),
40407
40491
  props: {
40408
40492
  handleDOMEvents: {
40409
- contextmenu: (_, event) => {
40493
+ contextmenu: (view, event) => {
40410
40494
  const target = event.target;
40411
40495
  const linkElement = target.closest("a[href]");
40412
40496
  if (linkElement) {
40413
40497
  const href = linkElement.getAttribute("href") || "";
40414
40498
  const text = linkElement.textContent || "";
40415
- logger.debug("\uD83D\uDD17 Link right-clicked:", { href, text });
40499
+ const pos = view.posAtDOM(linkElement, 0);
40500
+ if (pos < 0)
40501
+ return false;
40502
+ const $pos = view.state.doc.resolve(pos);
40503
+ const markRange = getMarkRange($pos, view.state.schema.marks.link, { href });
40504
+ const from2 = markRange?.from ?? pos;
40505
+ const to = markRange?.to ?? pos + text.length;
40506
+ logger.debug("\uD83D\uDD17 Link right-clicked:", { href, text, from: from2, to });
40416
40507
  if (href) {
40417
- handleContextMenu(event, { href, text });
40508
+ handleContextMenu(event, {
40509
+ href,
40510
+ text,
40511
+ from: from2,
40512
+ to
40513
+ });
40418
40514
  return true;
40419
40515
  }
40420
40516
  }
40421
40517
  return false;
40422
40518
  },
40423
- click: (_, event) => {
40519
+ click: (view, event) => {
40424
40520
  const target = event.target;
40425
40521
  const linkElement = target.closest("a[href]");
40426
40522
  if (linkElement) {
40427
40523
  const href = linkElement.getAttribute("href") || "";
40428
40524
  const text = linkElement.textContent || "";
40525
+ const pos = view.posAtDOM(linkElement, 0);
40526
+ if (pos < 0)
40527
+ return false;
40528
+ const $pos = view.state.doc.resolve(pos);
40529
+ const markRange = getMarkRange($pos, view.state.schema.marks.link, { href });
40530
+ const from2 = markRange?.from ?? pos;
40531
+ const to = markRange?.to ?? pos + text.length;
40429
40532
  logger.debug("\uD83D\uDD17 Link clicked:", {
40430
40533
  href,
40431
40534
  text,
40432
40535
  ctrlKey: event.ctrlKey,
40433
40536
  metaKey: event.metaKey,
40434
- shiftKey: event.shiftKey
40537
+ shiftKey: event.shiftKey,
40538
+ from: from2,
40539
+ to
40435
40540
  });
40436
40541
  if (href) {
40437
40542
  event.preventDefault();
40438
40543
  event.stopPropagation();
40439
- handleContextMenu(event, { href, text });
40544
+ handleContextMenu(event, {
40545
+ href,
40546
+ text,
40547
+ from: from2,
40548
+ to
40549
+ });
40440
40550
  return true;
40441
40551
  }
40442
40552
  }
@@ -41176,7 +41286,9 @@ var handleMarkdownPaste = async ({
41176
41286
  markdownToTipTapOptions
41177
41287
  }) => {
41178
41288
  editor.commands.deleteSelection();
41289
+ const startPos = editor.state.selection.from;
41179
41290
  insertPlainText(editor, plainText);
41291
+ const endPos = editor.state.selection.from;
41180
41292
  if (plainText.length >= largeTextThreshold) {
41181
41293
  logger2.info("\uD83D\uDCCB Large text detected - keeping as plain text to prevent performance issues");
41182
41294
  return;
@@ -41185,17 +41297,19 @@ var handleMarkdownPaste = async ({
41185
41297
  setIsProcessing(true);
41186
41298
  setProcessingProgress({ processed: 0, total: plainText.split(`
41187
41299
  `).length });
41188
- const currentPos = editor.state.selection.from;
41189
- const insertionStart = currentPos - plainText.length;
41190
41300
  try {
41191
- editor.commands.deleteRange({ from: insertionStart, to: currentPos });
41192
- editor.commands.setTextSelection(insertionStart);
41193
- await MarkdownTipTapConverter.processMarkdownInSmallChunksWithRender(plainText, editor, (processed, total) => {
41194
- setProcessingProgress({ processed, total });
41195
- }, markdownToTipTapOptions);
41301
+ if (endPos > startPos) {
41302
+ editor.commands.deleteRange({ from: startPos, to: endPos });
41303
+ editor.commands.setTextSelection(startPos);
41304
+ await MarkdownTipTapConverter.processMarkdownInSmallChunksWithRender(plainText, editor, (processed, total) => {
41305
+ setProcessingProgress({ processed, total });
41306
+ }, markdownToTipTapOptions);
41307
+ } else {
41308
+ logger2.warn("⚠️ Nothing inserted or invalid range detected");
41309
+ }
41196
41310
  } catch (error) {
41197
41311
  logger2.warn("⚠️ Sequential rendering failed, keeping plain text:", error);
41198
- editor.commands.setTextSelection(insertionStart);
41312
+ editor.commands.setTextSelection(startPos);
41199
41313
  insertPlainText(editor, plainText);
41200
41314
  } finally {
41201
41315
  editor.__isProcessing = false;
@@ -41522,6 +41636,7 @@ var useMarkdownEditor = ({
41522
41636
  handleTableContextMenu
41523
41637
  }) => {
41524
41638
  const lowlight = createLowlight(grammars);
41639
+ const lastEmittedDocRef = useRef3(null);
41525
41640
  const editor = useEditor({
41526
41641
  enableContentCheck: false,
41527
41642
  emitContentError: true,
@@ -41598,39 +41713,39 @@ var useMarkdownEditor = ({
41598
41713
  if (isUpdating || editor2.__preventUpdate || isProcessing) {
41599
41714
  return;
41600
41715
  }
41716
+ const { doc: doc3 } = editor2.state;
41601
41717
  const json2 = editor2.getJSON();
41602
41718
  setContent2(json2);
41603
41719
  if (onContentChange) {
41604
41720
  onContentChange(json2);
41605
41721
  }
41606
- if (onChange) {
41722
+ if (onChange || onMarkdownChange) {
41607
41723
  try {
41608
41724
  const markdown2 = JsonToMarkdownConverter_default.convertToMarkdown(json2);
41609
- onChange(markdown2);
41610
- } catch (error) {
41611
- logger3.warn("⚠️ Markdown conversion failed in onUpdate:", error);
41612
- }
41613
- }
41614
- if (onMarkdownChange) {
41615
- try {
41616
- const markdown2 = JsonToMarkdownConverter_default.convertToMarkdown(json2);
41617
- onMarkdownChange(markdown2);
41725
+ if (onChange)
41726
+ onChange(markdown2);
41727
+ if (onMarkdownChange)
41728
+ onMarkdownChange(markdown2);
41729
+ lastEmittedDocRef.current = doc3;
41618
41730
  } catch (error) {
41619
41731
  logger3.warn("⚠️ Markdown conversion failed in onUpdate:", error);
41620
41732
  }
41621
41733
  }
41622
41734
  },
41623
41735
  onBlur: ({ editor: editor2 }) => {
41624
- if (onMarkdownChange) {
41736
+ if (lastEmittedDocRef.current && editor2.state.doc.eq(lastEmittedDocRef.current)) {
41737
+ return;
41738
+ }
41739
+ const hasListeners = onChange || onMarkdownChange;
41740
+ if (hasListeners) {
41625
41741
  try {
41626
41742
  const json2 = editor2.getJSON();
41627
41743
  const markdown2 = JsonToMarkdownConverter_default.convertToMarkdown(json2);
41628
- if (onChange) {
41744
+ if (onChange)
41629
41745
  onChange(markdown2);
41630
- }
41631
- if (onMarkdownChange) {
41746
+ if (onMarkdownChange)
41632
41747
  onMarkdownChange(markdown2);
41633
- }
41748
+ lastEmittedDocRef.current = editor2.state.doc;
41634
41749
  } catch (error) {
41635
41750
  logger3.warn("⚠️ Markdown conversion failed in onBlur:", error);
41636
41751
  }
@@ -42265,7 +42380,7 @@ var MarkdownSyntaxStatus = ({
42265
42380
  import React7 from "react";
42266
42381
 
42267
42382
  // src/components/EmojiPicker.tsx
42268
- import { useEffect as useEffect9, useMemo as useMemo2, useRef as useRef3, useState as useState10 } from "react";
42383
+ import { useEffect as useEffect9, useMemo as useMemo2, useRef as useRef4, useState as useState10 } from "react";
42269
42384
 
42270
42385
  // src/constants/emojiData.ts
42271
42386
  var EMOJI_CATEGORIES = [
@@ -42769,7 +42884,7 @@ var EmojiPicker = ({
42769
42884
  }) => {
42770
42885
  const [activeGroup, setActiveGroup] = useState10("smileys_people");
42771
42886
  const [query, setQuery] = useState10("");
42772
- const pickerRef = useRef3(null);
42887
+ const pickerRef = useRef4(null);
42773
42888
  useEffect9(() => {
42774
42889
  const handleClickOutside = (event) => {
42775
42890
  if (pickerRef.current && !pickerRef.current.contains(event.target)) {
@@ -42811,11 +42926,10 @@ var EmojiPicker = ({
42811
42926
  const g = EMOJI_CATEGORY_GROUPS.find((x) => x.id === activeGroup);
42812
42927
  return g?.categories ?? [];
42813
42928
  }, [activeGroup]);
42814
- return /* @__PURE__ */ jsxDEV8("dialog", {
42929
+ return /* @__PURE__ */ jsxDEV8("div", {
42815
42930
  ref: pickerRef,
42816
- className: "mw-emoji-picker bg-popover text-popover-foreground border border-border shadow-xl rounded-xl",
42931
+ className: "mw-emoji-picker bg-popover text-popover-foreground border border-border shadow-lg ring-1 ring-black ring-opacity-5 rounded-[calc(var(--radius)+4px)]",
42817
42932
  "aria-label": t(I18N_KEYS.emoji.pickerTitle, "Emoji picker"),
42818
- open: true,
42819
42933
  children: [
42820
42934
  /* @__PURE__ */ jsxDEV8("div", {
42821
42935
  className: "mw-emoji-search",
@@ -42917,7 +43031,7 @@ var EmojiPicker = ({
42917
43031
  };
42918
43032
 
42919
43033
  // src/components/ImagePicker.tsx
42920
- import { useEffect as useEffect10, useRef as useRef4, useState as useState11 } from "react";
43034
+ import { useEffect as useEffect10, useRef as useRef5, useState as useState11 } from "react";
42921
43035
  import { jsxDEV as jsxDEV9 } from "react/jsx-dev-runtime";
42922
43036
  var ImagePicker = ({
42923
43037
  onInsertMarkdown,
@@ -42927,7 +43041,7 @@ var ImagePicker = ({
42927
43041
  }) => {
42928
43042
  const [url, setUrl] = useState11("");
42929
43043
  const [alt, setAlt] = useState11("");
42930
- const pickerRef = useRef4(null);
43044
+ const pickerRef = useRef5(null);
42931
43045
  useEffect10(() => {
42932
43046
  const handleClickOutside = (event) => {
42933
43047
  if (pickerRef.current && !pickerRef.current.contains(event.target)) {
@@ -43224,54 +43338,43 @@ var HeadingMenu = ({
43224
43338
  ${isOpen ? "opacity-100 scale-100" : "opacity-0 scale-95 pointer-events-none"}
43225
43339
  `,
43226
43340
  children: /* @__PURE__ */ jsxDEV11("div", {
43227
- className: "py-ui-y",
43341
+ className: "flex flex-col py-1",
43228
43342
  children: headingLevels.map((heading) => /* @__PURE__ */ jsxDEV11("button", {
43229
43343
  type: "button",
43344
+ className: "w-full flex items-center px-4 py-2 hover:bg-accent hover:text-accent-foreground transition-colors text-left group",
43230
43345
  onClick: () => {
43231
43346
  onInsertMarkdown(heading.markdown);
43232
43347
  onClose();
43233
43348
  },
43234
- children: /* @__PURE__ */ jsxDEV11("div", {
43235
- className: "flex items-center w-full",
43236
- children: [
43237
- /* @__PURE__ */ jsxDEV11("div", {
43349
+ children: [
43350
+ /* @__PURE__ */ jsxDEV11("div", {
43351
+ className: "flex-shrink-0 w-12 h-8 rounded border flex items-center justify-center font-bold shadow-sm bg-background border-border text-foreground group-hover:border-accent-foreground/30 transition-colors",
43352
+ children: /* @__PURE__ */ jsxDEV11("span", {
43238
43353
  className: `
43239
- flex-1 px-ui-x py-ui-y rounded-md transition-colors duration-150
43240
- hover:bg-accent hover:text-accent-foreground
43241
- `,
43242
- children: /* @__PURE__ */ jsxDEV11("div", {
43243
- className: "flex items-center space-x-3",
43244
- children: /* @__PURE__ */ jsxDEV11("div", {
43245
- className: "flex-shrink-0 w-12 h-8 rounded-ui border flex items-center justify-center font-bold shadow-sm bg-background border-border text-foreground",
43246
- children: /* @__PURE__ */ jsxDEV11("span", {
43247
- className: `
43248
- ${heading.level === 1 ? "text-[18px]" : ""}
43249
- ${heading.level === 2 ? "text-[16px]" : ""}
43250
- ${heading.level === 3 ? "text-[14px]" : ""}
43251
- ${heading.level >= 4 ? "text-[12px]" : ""}
43252
- `,
43253
- children: heading.preview
43254
- }, undefined, false, undefined, this)
43255
- }, undefined, false, undefined, this)
43256
- }, undefined, false, undefined, this)
43257
- }, undefined, false, undefined, this),
43258
- /* @__PURE__ */ jsxDEV11("div", {
43259
- className: "flex-shrink-0 ml-3",
43260
- children: /* @__PURE__ */ jsxDEV11("div", {
43261
- className: `
43262
- truncate max-w-[200px] text-popover-foreground
43263
- ${heading.level === 1 ? "text-[22px] font-bold leading-[28px]" : ""}
43264
- ${heading.level === 2 ? "text-[18px] font-bold leading-[24px]" : ""}
43265
- ${heading.level === 3 ? "text-[16px] font-semibold leading-[22px]" : ""}
43266
- ${heading.level === 4 ? "text-[14px] font-semibold leading-[20px]" : ""}
43267
- ${heading.level === 5 ? "text-[13px] font-semibold leading-[18px]" : ""}
43268
- `,
43269
- children: `${t(I18N_KEYS.heading)}${heading.level}`
43270
- }, undefined, false, undefined, this)
43354
+ ${heading.level === 1 ? "text-[18px]" : ""}
43355
+ ${heading.level === 2 ? "text-[16px]" : ""}
43356
+ ${heading.level === 3 ? "text-[14px]" : ""}
43357
+ ${heading.level >= 4 ? "text-[12px]" : ""}
43358
+ `,
43359
+ children: heading.preview
43271
43360
  }, undefined, false, undefined, this)
43272
- ]
43273
- }, undefined, true, undefined, this)
43274
- }, heading.level, false, undefined, this))
43361
+ }, undefined, false, undefined, this),
43362
+ /* @__PURE__ */ jsxDEV11("div", {
43363
+ className: "ml-3 flex-1",
43364
+ children: /* @__PURE__ */ jsxDEV11("div", {
43365
+ className: `
43366
+ truncate max-w-[180px]
43367
+ ${heading.level === 1 ? "text-[20px] font-bold" : ""}
43368
+ ${heading.level === 2 ? "text-[18px] font-bold" : ""}
43369
+ ${heading.level === 3 ? "text-[16px] font-semibold" : ""}
43370
+ ${heading.level === 4 ? "text-[14px] font-semibold" : ""}
43371
+ ${heading.level === 5 ? "text-[13px] font-medium" : ""}
43372
+ `,
43373
+ children: `${t(I18N_KEYS.heading)}${heading.level}`
43374
+ }, undefined, false, undefined, this)
43375
+ }, undefined, false, undefined, this)
43376
+ ]
43377
+ }, heading.level, true, undefined, this))
43275
43378
  }, undefined, false, undefined, this)
43276
43379
  }, undefined, false, undefined, this)
43277
43380
  ]
@@ -43685,7 +43788,7 @@ var MarkdownToolbar = ({
43685
43788
  disabled
43686
43789
  }, undefined, false, undefined, this),
43687
43790
  item.icon === Smile && showEmojiPicker && /* @__PURE__ */ jsxDEV14("div", {
43688
- className: "absolute top-full left-0 mt-1 z-20",
43791
+ className: "absolute top-full left-1/2 -translate-x-1/2 mt-ui-y z-20",
43689
43792
  children: /* @__PURE__ */ jsxDEV14(EmojiPicker, {
43690
43793
  onSelect: handleEmojiSelect,
43691
43794
  onClose: () => setShowEmojiPicker(false),
@@ -43694,7 +43797,7 @@ var MarkdownToolbar = ({
43694
43797
  }, undefined, false, undefined, this)
43695
43798
  }, undefined, false, undefined, this),
43696
43799
  item.icon === Image3 && showImagePicker && /* @__PURE__ */ jsxDEV14("div", {
43697
- className: "absolute top-full left-0 mt-1 z-20",
43800
+ className: "absolute top-full left-1/2 -translate-x-1/2 mt-ui-y z-20",
43698
43801
  children: /* @__PURE__ */ jsxDEV14(ImagePicker, {
43699
43802
  onInsertMarkdown: handleInsertImageMarkdown,
43700
43803
  onClose: () => setShowImagePicker(false),
@@ -44556,6 +44659,8 @@ var MarkdownEditor = ({
44556
44659
  setProcessingProgress
44557
44660
  } = useEditorState2();
44558
44661
  const editorElementRef = React8.useRef(null);
44662
+ const abortControllerRef = React8.useRef(null);
44663
+ const lastProcessedContentRef = React8.useRef(undefined);
44559
44664
  const {
44560
44665
  linkContextMenu,
44561
44666
  tableContextMenu,
@@ -44616,22 +44721,34 @@ var MarkdownEditor = ({
44616
44721
  useEffect14(() => {
44617
44722
  const processInitialMarkdown = async () => {
44618
44723
  const contentToProcess = value !== undefined ? value : initialContent;
44724
+ if (contentToProcess === lastProcessedContentRef.current) {
44725
+ return;
44726
+ }
44619
44727
  if (!editor)
44620
44728
  return;
44729
+ if (abortControllerRef.current) {
44730
+ abortControllerRef.current.abort();
44731
+ }
44732
+ const controller = new AbortController;
44733
+ abortControllerRef.current = controller;
44621
44734
  if (!contentToProcess || !contentToProcess.trim()) {
44622
- if (!editor.isEmpty) {
44735
+ if (!editor.isEmpty && !controller.signal.aborted) {
44623
44736
  editor.commands.clearContent();
44737
+ lastProcessedContentRef.current = contentToProcess;
44624
44738
  }
44625
44739
  return;
44626
44740
  }
44627
44741
  const trimmed = contentToProcess.trim();
44628
44742
  try {
44629
44743
  if (editor.isFocused && editable) {
44744
+ lastProcessedContentRef.current = contentToProcess;
44630
44745
  return;
44631
44746
  }
44632
44747
  const json2 = await MarkdownTipTapConverter.markdownToTipTapJson(trimmed, {
44633
44748
  publicImagePathPrefix
44634
44749
  });
44750
+ if (controller.signal.aborted)
44751
+ return;
44635
44752
  const codeBlocks = json2?.content?.filter((node) => node.type === "codeBlock") || [];
44636
44753
  if (codeBlocks.length > 0) {
44637
44754
  codeBlocks.forEach((block, idx) => {
@@ -44642,7 +44759,10 @@ var MarkdownEditor = ({
44642
44759
  });
44643
44760
  }
44644
44761
  editor.commands.setContent(json2);
44762
+ lastProcessedContentRef.current = contentToProcess;
44645
44763
  } catch (error) {
44764
+ if (controller.signal.aborted)
44765
+ return;
44646
44766
  logger5.warn("[MarkdownEditor] Automatic Markdown conversion failed:", error);
44647
44767
  const lines = trimmed.split(`
44648
44768
  `);
@@ -44653,11 +44773,17 @@ var MarkdownEditor = ({
44653
44773
  content: line.length > 0 ? [{ type: "text", text: line }] : []
44654
44774
  }))
44655
44775
  });
44776
+ lastProcessedContentRef.current = contentToProcess;
44656
44777
  }
44657
44778
  };
44658
44779
  if (editor) {
44659
44780
  processInitialMarkdown();
44660
44781
  }
44782
+ return () => {
44783
+ if (abortControllerRef.current) {
44784
+ abortControllerRef.current.abort();
44785
+ }
44786
+ };
44661
44787
  }, [editor, initialContent, value, editable, publicImagePathPrefix]);
44662
44788
  useEffect14(() => {
44663
44789
  if (editor && editor.isEditable !== editable) {
@@ -44710,33 +44836,19 @@ var MarkdownEditor = ({
44710
44836
  editor.__preventUpdate = true;
44711
44837
  try {
44712
44838
  const { state, dispatch } = editor.view;
44713
- let linkUpdated = false;
44714
- state.doc.descendants((node, pos) => {
44715
- if (linkUpdated)
44716
- return false;
44717
- if (node.isText && node.marks) {
44718
- const linkMark = node.marks.find((mark) => mark.type.name === "link");
44719
- if (linkMark && linkMark.attrs.href === linkContextMenu.linkData?.href && node.text === linkContextMenu.linkData?.text) {
44720
- if (!state.schema.marks.link) {
44721
- logger5.warn("Link mark type not found in schema");
44722
- return false;
44723
- }
44724
- const from2 = pos;
44725
- const to = pos + node.nodeSize;
44726
- const newLinkMark = state.schema.marks.link.create({ href: newLinkData.href });
44727
- const transaction = state.tr;
44728
- transaction.delete(from2, to);
44729
- transaction.insert(from2, state.schema.text(newLinkData.text, [newLinkMark]));
44730
- dispatch(transaction);
44731
- linkUpdated = true;
44732
- return false;
44733
- }
44734
- }
44735
- return true;
44736
- });
44737
- if (!linkUpdated) {
44738
- logger5.warn("Link not found for update");
44839
+ const { from: from2, to } = linkContextMenu.linkData;
44840
+ const node = state.doc.nodeAt(from2);
44841
+ if (typeof from2 === "number" && typeof to === "number") {
44842
+ const newLinkMark = state.schema.marks.link.create({ href: newLinkData.href });
44843
+ const transaction = state.tr;
44844
+ transaction.delete(from2, to);
44845
+ transaction.insert(from2, state.schema.text(newLinkData.text, [newLinkMark]));
44846
+ dispatch(transaction);
44847
+ } else {
44848
+ logger5.warn("Use of old link editing fallback");
44739
44849
  }
44850
+ } catch (error) {
44851
+ logger5.error("Link update failed", error);
44740
44852
  } finally {
44741
44853
  setTimeout(() => {
44742
44854
  editor.__preventUpdate = originalPreventUpdate;
@@ -45072,5 +45184,5 @@ export {
45072
45184
  CodeBlockNodeView
45073
45185
  };
45074
45186
 
45075
- //# debugId=70312CAF74302EFC64756E2164756E21
45187
+ //# debugId=C55D38675362963664756E2164756E21
45076
45188
  //# sourceMappingURL=index.js.map