@tiptap/core 3.0.0-next.3 → 3.0.0-next.5

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.
Files changed (146) hide show
  1. package/LICENSE.md +21 -0
  2. package/README.md +5 -1
  3. package/dist/index.cjs +2627 -2651
  4. package/dist/index.cjs.map +1 -1
  5. package/dist/index.d.cts +2423 -2688
  6. package/dist/index.d.ts +2423 -2688
  7. package/dist/index.js +2639 -2684
  8. package/dist/index.js.map +1 -1
  9. package/dist/jsx-runtime/jsx-runtime.cjs +56 -0
  10. package/dist/jsx-runtime/jsx-runtime.cjs.map +1 -0
  11. package/dist/jsx-runtime/jsx-runtime.d.cts +22 -0
  12. package/dist/jsx-runtime/jsx-runtime.d.ts +22 -0
  13. package/dist/jsx-runtime/jsx-runtime.js +26 -0
  14. package/dist/jsx-runtime/jsx-runtime.js.map +1 -0
  15. package/jsx-runtime/index.cjs +1 -0
  16. package/jsx-runtime/index.d.cts +1 -0
  17. package/jsx-runtime/index.d.ts +1 -0
  18. package/jsx-runtime/index.js +1 -0
  19. package/package.json +27 -6
  20. package/src/CommandManager.ts +2 -9
  21. package/src/Editor.ts +191 -94
  22. package/src/EventEmitter.ts +7 -10
  23. package/src/Extendable.ts +483 -0
  24. package/src/Extension.ts +5 -496
  25. package/src/ExtensionManager.ts +81 -135
  26. package/src/InputRule.ts +35 -48
  27. package/src/Mark.ts +135 -623
  28. package/src/MarkView.ts +66 -0
  29. package/src/Node.ts +325 -829
  30. package/src/NodePos.ts +1 -3
  31. package/src/NodeView.ts +10 -20
  32. package/src/PasteRule.ts +43 -55
  33. package/src/Tracker.ts +7 -9
  34. package/src/commands/blur.ts +14 -12
  35. package/src/commands/clearContent.ts +12 -5
  36. package/src/commands/clearNodes.ts +32 -30
  37. package/src/commands/command.ts +1 -1
  38. package/src/commands/createParagraphNear.ts +5 -3
  39. package/src/commands/cut.ts +12 -10
  40. package/src/commands/deleteCurrentNode.ts +23 -21
  41. package/src/commands/deleteNode.ts +18 -16
  42. package/src/commands/deleteRange.ts +10 -8
  43. package/src/commands/deleteSelection.ts +5 -3
  44. package/src/commands/enter.ts +6 -4
  45. package/src/commands/exitCode.ts +5 -3
  46. package/src/commands/extendMarkRange.ts +14 -12
  47. package/src/commands/first.ts +2 -4
  48. package/src/commands/focus.ts +51 -48
  49. package/src/commands/forEach.ts +2 -2
  50. package/src/commands/insertContent.ts +12 -14
  51. package/src/commands/insertContentAt.ts +105 -98
  52. package/src/commands/join.ts +20 -12
  53. package/src/commands/joinItemBackward.ts +16 -18
  54. package/src/commands/joinItemForward.ts +16 -18
  55. package/src/commands/joinTextblockBackward.ts +5 -3
  56. package/src/commands/joinTextblockForward.ts +5 -3
  57. package/src/commands/keyboardShortcut.ts +29 -34
  58. package/src/commands/lift.ts +10 -8
  59. package/src/commands/liftEmptyBlock.ts +6 -4
  60. package/src/commands/liftListItem.ts +6 -4
  61. package/src/commands/newlineInCode.ts +5 -3
  62. package/src/commands/resetAttributes.ts +36 -41
  63. package/src/commands/scrollIntoView.ts +9 -7
  64. package/src/commands/selectAll.ts +10 -8
  65. package/src/commands/selectNodeBackward.ts +5 -3
  66. package/src/commands/selectNodeForward.ts +5 -3
  67. package/src/commands/selectParentNode.ts +5 -3
  68. package/src/commands/selectTextblockEnd.ts +5 -3
  69. package/src/commands/selectTextblockStart.ts +5 -3
  70. package/src/commands/setContent.ts +37 -36
  71. package/src/commands/setMark.ts +55 -57
  72. package/src/commands/setMeta.ts +7 -5
  73. package/src/commands/setNode.ts +32 -30
  74. package/src/commands/setNodeSelection.ts +11 -9
  75. package/src/commands/setTextSelection.ts +15 -13
  76. package/src/commands/sinkListItem.ts +6 -4
  77. package/src/commands/splitBlock.ts +67 -76
  78. package/src/commands/splitListItem.ts +93 -106
  79. package/src/commands/toggleList.ts +73 -71
  80. package/src/commands/toggleMark.ts +11 -9
  81. package/src/commands/toggleNode.ts +18 -16
  82. package/src/commands/toggleWrap.ts +10 -8
  83. package/src/commands/undoInputRule.ts +31 -29
  84. package/src/commands/unsetAllMarks.ts +16 -14
  85. package/src/commands/unsetMark.ts +27 -25
  86. package/src/commands/updateAttributes.ts +92 -100
  87. package/src/commands/wrapIn.ts +6 -4
  88. package/src/commands/wrapInList.ts +6 -4
  89. package/src/extensions/clipboardTextSerializer.ts +2 -4
  90. package/src/extensions/delete.ts +89 -0
  91. package/src/extensions/focusEvents.ts +2 -6
  92. package/src/extensions/index.ts +1 -0
  93. package/src/extensions/keymap.ts +58 -50
  94. package/src/extensions/paste.ts +0 -1
  95. package/src/extensions/tabindex.ts +1 -1
  96. package/src/helpers/combineTransactionSteps.ts +1 -4
  97. package/src/helpers/createChainableState.ts +1 -4
  98. package/src/helpers/createDocument.ts +1 -3
  99. package/src/helpers/createNodeFromContent.ts +4 -10
  100. package/src/helpers/findChildrenInRange.ts +1 -5
  101. package/src/helpers/findParentNode.ts +3 -1
  102. package/src/helpers/flattenExtensions.ts +30 -0
  103. package/src/helpers/getAttributes.ts +1 -4
  104. package/src/helpers/getAttributesFromExtensions.ts +28 -37
  105. package/src/helpers/getChangedRanges.ts +13 -11
  106. package/src/helpers/getExtensionField.ts +11 -11
  107. package/src/helpers/getMarkAttributes.ts +1 -4
  108. package/src/helpers/getMarkRange.ts +5 -15
  109. package/src/helpers/getMarkType.ts +1 -3
  110. package/src/helpers/getNodeAttributes.ts +1 -4
  111. package/src/helpers/getNodeType.ts +1 -3
  112. package/src/helpers/getRenderedAttributes.ts +1 -3
  113. package/src/helpers/getSchema.ts +2 -2
  114. package/src/helpers/getSchemaByResolvedExtensions.ts +45 -77
  115. package/src/helpers/getSplittedAttributes.ts +4 -4
  116. package/src/helpers/getTextContentFromNodes.ts +8 -11
  117. package/src/helpers/index.ts +4 -0
  118. package/src/helpers/injectExtensionAttributesToParseRule.ts +1 -1
  119. package/src/helpers/isActive.ts +1 -5
  120. package/src/helpers/isExtensionRulesEnabled.ts +1 -3
  121. package/src/helpers/isNodeEmpty.ts +2 -2
  122. package/src/helpers/resolveExtensions.ts +25 -0
  123. package/src/helpers/resolveFocusPosition.ts +3 -14
  124. package/src/helpers/rewriteUnknownContent.ts +149 -0
  125. package/src/helpers/sortExtensions.ts +26 -0
  126. package/src/index.ts +3 -7
  127. package/src/inputRules/markInputRule.ts +1 -5
  128. package/src/inputRules/nodeInputRule.ts +2 -9
  129. package/src/inputRules/textInputRule.ts +1 -4
  130. package/src/inputRules/textblockTypeInputRule.ts +2 -8
  131. package/src/inputRules/wrappingInputRule.ts +13 -19
  132. package/src/jsx-runtime.ts +64 -0
  133. package/src/pasteRules/markPasteRule.ts +1 -3
  134. package/src/pasteRules/nodePasteRule.ts +2 -8
  135. package/src/pasteRules/textPasteRule.ts +1 -4
  136. package/src/types.ts +529 -174
  137. package/src/utilities/createStyleTag.ts +3 -1
  138. package/src/utilities/deleteProps.ts +7 -11
  139. package/src/utilities/elementFromString.ts +3 -0
  140. package/src/utilities/findDuplicates.ts +4 -1
  141. package/src/utilities/index.ts +1 -0
  142. package/src/utilities/isFunction.ts +1 -0
  143. package/src/utilities/isMacOS.ts +1 -3
  144. package/src/utilities/isiOS.ts +5 -10
  145. package/src/utilities/mergeAttributes.ts +17 -7
  146. package/src/utilities/removeDuplicates.ts +1 -3
@@ -1,24 +1,28 @@
1
1
  import { keymap } from '@tiptap/pm/keymap'
2
2
  import { Schema } from '@tiptap/pm/model'
3
3
  import { Plugin } from '@tiptap/pm/state'
4
- import { NodeViewConstructor } from '@tiptap/pm/view'
4
+ import { MarkViewConstructor, NodeViewConstructor } from '@tiptap/pm/view'
5
5
 
6
6
  import type { Editor } from './Editor.js'
7
- import { getAttributesFromExtensions } from './helpers/getAttributesFromExtensions.js'
8
- import { getExtensionField } from './helpers/getExtensionField.js'
9
- import { getNodeType } from './helpers/getNodeType.js'
10
- import { getRenderedAttributes } from './helpers/getRenderedAttributes.js'
11
- import { getSchemaByResolvedExtensions } from './helpers/getSchemaByResolvedExtensions.js'
12
- import { getSchemaTypeByName } from './helpers/getSchemaTypeByName.js'
13
- import { isExtensionRulesEnabled } from './helpers/isExtensionRulesEnabled.js'
14
- import { splitExtensions } from './helpers/splitExtensions.js'
15
- import type { NodeConfig } from './index.js'
7
+ import {
8
+ flattenExtensions,
9
+ getAttributesFromExtensions,
10
+ getExtensionField,
11
+ getNodeType,
12
+ getRenderedAttributes,
13
+ getSchemaByResolvedExtensions,
14
+ getSchemaTypeByName,
15
+ isExtensionRulesEnabled,
16
+ resolveExtensions,
17
+ sortExtensions,
18
+ splitExtensions,
19
+ } from './helpers/index.js'
20
+ import { type MarkConfig, type NodeConfig, type Storage, getMarkType } from './index.js'
16
21
  import { InputRule, inputRulesPlugin } from './InputRule.js'
17
22
  import { Mark } from './Mark.js'
18
23
  import { PasteRule, pasteRulesPlugin } from './PasteRule.js'
19
24
  import { AnyConfig, Extensions, RawCommands } from './types.js'
20
25
  import { callOrReturn } from './utilities/callOrReturn.js'
21
- import { findDuplicates } from './utilities/findDuplicates.js'
22
26
 
23
27
  export class ExtensionManager {
24
28
  editor: Editor
@@ -31,87 +35,16 @@ export class ExtensionManager {
31
35
 
32
36
  constructor(extensions: Extensions, editor: Editor) {
33
37
  this.editor = editor
34
- this.extensions = ExtensionManager.resolve(extensions)
38
+ this.extensions = resolveExtensions(extensions)
35
39
  this.schema = getSchemaByResolvedExtensions(this.extensions, editor)
36
40
  this.setupExtensions()
37
41
  }
38
42
 
39
- /**
40
- * Returns a flattened and sorted extension list while
41
- * also checking for duplicated extensions and warns the user.
42
- * @param extensions An array of Tiptap extensions
43
- * @returns An flattened and sorted array of Tiptap extensions
44
- */
45
- static resolve(extensions: Extensions): Extensions {
46
- const resolvedExtensions = ExtensionManager.sort(ExtensionManager.flatten(extensions))
47
- const duplicatedNames = findDuplicates(resolvedExtensions.map(extension => extension.name))
48
-
49
- if (duplicatedNames.length) {
50
- console.warn(
51
- `[tiptap warn]: Duplicate extension names found: [${duplicatedNames
52
- .map(item => `'${item}'`)
53
- .join(', ')}]. This can lead to issues.`,
54
- )
55
- }
43
+ static resolve = resolveExtensions
56
44
 
57
- return resolvedExtensions
58
- }
45
+ static sort = sortExtensions
59
46
 
60
- /**
61
- * Create a flattened array of extensions by traversing the `addExtensions` field.
62
- * @param extensions An array of Tiptap extensions
63
- * @returns A flattened array of Tiptap extensions
64
- */
65
- static flatten(extensions: Extensions): Extensions {
66
- return (
67
- extensions
68
- .map(extension => {
69
- const context = {
70
- name: extension.name,
71
- options: extension.options,
72
- storage: extension.storage,
73
- }
74
-
75
- const addExtensions = getExtensionField<AnyConfig['addExtensions']>(
76
- extension,
77
- 'addExtensions',
78
- context,
79
- )
80
-
81
- if (addExtensions) {
82
- return [extension, ...this.flatten(addExtensions())]
83
- }
84
-
85
- return extension
86
- })
87
- // `Infinity` will break TypeScript so we set a number that is probably high enough
88
- .flat(10)
89
- )
90
- }
91
-
92
- /**
93
- * Sort extensions by priority.
94
- * @param extensions An array of Tiptap extensions
95
- * @returns A sorted array of Tiptap extensions by priority
96
- */
97
- static sort(extensions: Extensions): Extensions {
98
- const defaultPriority = 100
99
-
100
- return extensions.sort((a, b) => {
101
- const priorityA = getExtensionField<AnyConfig['priority']>(a, 'priority') || defaultPriority
102
- const priorityB = getExtensionField<AnyConfig['priority']>(b, 'priority') || defaultPriority
103
-
104
- if (priorityA > priorityB) {
105
- return -1
106
- }
107
-
108
- if (priorityA < priorityB) {
109
- return 1
110
- }
111
-
112
- return 0
113
- })
114
- }
47
+ static flatten = flattenExtensions
115
48
 
116
49
  /**
117
50
  * Get all commands from the extensions.
@@ -122,16 +55,12 @@ export class ExtensionManager {
122
55
  const context = {
123
56
  name: extension.name,
124
57
  options: extension.options,
125
- storage: extension.storage,
58
+ storage: this.editor.extensionStorage[extension.name as keyof Storage],
126
59
  editor: this.editor,
127
60
  type: getSchemaTypeByName(extension.name, this.schema),
128
61
  }
129
62
 
130
- const addCommands = getExtensionField<AnyConfig['addCommands']>(
131
- extension,
132
- 'addCommands',
133
- context,
134
- )
63
+ const addCommands = getExtensionField<AnyConfig['addCommands']>(extension, 'addCommands', context)
135
64
 
136
65
  if (!addCommands) {
137
66
  return commands
@@ -156,7 +85,7 @@ export class ExtensionManager {
156
85
  // so it feels more natural to run plugins at the end of an array first.
157
86
  // That’s why we have to reverse the `extensions` array and sort again
158
87
  // based on the `priority` option.
159
- const extensions = ExtensionManager.sort([...this.extensions].reverse())
88
+ const extensions = sortExtensions([...this.extensions].reverse())
160
89
 
161
90
  const inputRules: InputRule[] = []
162
91
  const pasteRules: PasteRule[] = []
@@ -166,7 +95,7 @@ export class ExtensionManager {
166
95
  const context = {
167
96
  name: extension.name,
168
97
  options: extension.options,
169
- storage: extension.storage,
98
+ storage: this.editor.extensionStorage[extension.name as keyof Storage],
170
99
  editor,
171
100
  type: getSchemaTypeByName(extension.name, this.schema),
172
101
  }
@@ -182,7 +111,7 @@ export class ExtensionManager {
182
111
  let defaultBindings: Record<string, () => boolean> = {}
183
112
 
184
113
  // bind exit handling
185
- if (extension.type === 'mark' && getExtensionField<AnyConfig['exitable']>(extension, 'exitable', context)) {
114
+ if (extension.type === 'mark' && getExtensionField<MarkConfig['exitable']>(extension, 'exitable', context)) {
186
115
  defaultBindings.ArrowRight = () => Mark.handleExit({ editor, mark: extension as Mark })
187
116
  }
188
117
 
@@ -200,21 +129,13 @@ export class ExtensionManager {
200
129
 
201
130
  plugins.push(keyMapPlugin)
202
131
 
203
- const addInputRules = getExtensionField<AnyConfig['addInputRules']>(
204
- extension,
205
- 'addInputRules',
206
- context,
207
- )
132
+ const addInputRules = getExtensionField<AnyConfig['addInputRules']>(extension, 'addInputRules', context)
208
133
 
209
134
  if (isExtensionRulesEnabled(extension, editor.options.enableInputRules) && addInputRules) {
210
135
  inputRules.push(...addInputRules())
211
136
  }
212
137
 
213
- const addPasteRules = getExtensionField<AnyConfig['addPasteRules']>(
214
- extension,
215
- 'addPasteRules',
216
- context,
217
- )
138
+ const addPasteRules = getExtensionField<AnyConfig['addPasteRules']>(extension, 'addPasteRules', context)
218
139
 
219
140
  if (isExtensionRulesEnabled(extension, editor.options.enablePasteRules) && addPasteRules) {
220
141
  pasteRules.push(...addPasteRules())
@@ -269,33 +190,21 @@ export class ExtensionManager {
269
190
  nodeExtensions
270
191
  .filter(extension => !!getExtensionField(extension, 'addNodeView'))
271
192
  .map(extension => {
272
- const extensionAttributes = this.attributes.filter(
273
- attribute => attribute.type === extension.name,
274
- )
193
+ const extensionAttributes = this.attributes.filter(attribute => attribute.type === extension.name)
275
194
  const context = {
276
195
  name: extension.name,
277
196
  options: extension.options,
278
- storage: extension.storage,
197
+ storage: this.editor.extensionStorage[extension.name as keyof Storage],
279
198
  editor,
280
199
  type: getNodeType(extension.name, this.schema),
281
200
  }
282
- const addNodeView = getExtensionField<NodeConfig['addNodeView']>(
283
- extension,
284
- 'addNodeView',
285
- context,
286
- )
201
+ const addNodeView = getExtensionField<NodeConfig['addNodeView']>(extension, 'addNodeView', context)
287
202
 
288
203
  if (!addNodeView) {
289
204
  return []
290
205
  }
291
206
 
292
- const nodeview: NodeViewConstructor = (
293
- node,
294
- view,
295
- getPos,
296
- decorations,
297
- innerDecorations,
298
- ) => {
207
+ const nodeview: NodeViewConstructor = (node, view, getPos, decorations, innerDecorations) => {
299
208
  const HTMLAttributes = getRenderedAttributes(node, extensionAttributes)
300
209
 
301
210
  return addNodeView()({
@@ -317,19 +226,64 @@ export class ExtensionManager {
317
226
  )
318
227
  }
319
228
 
229
+ get markViews(): Record<string, MarkViewConstructor> {
230
+ const { editor } = this
231
+ const { markExtensions } = splitExtensions(this.extensions)
232
+
233
+ return Object.fromEntries(
234
+ markExtensions
235
+ .filter(extension => !!getExtensionField(extension, 'addMarkView'))
236
+ .map(extension => {
237
+ const extensionAttributes = this.attributes.filter(attribute => attribute.type === extension.name)
238
+ const context = {
239
+ name: extension.name,
240
+ options: extension.options,
241
+ storage: this.editor.extensionStorage[extension.name as keyof Storage],
242
+ editor,
243
+ type: getMarkType(extension.name, this.schema),
244
+ }
245
+ const addMarkView = getExtensionField<MarkConfig['addMarkView']>(extension, 'addMarkView', context)
246
+
247
+ if (!addMarkView) {
248
+ return []
249
+ }
250
+
251
+ const markView: MarkViewConstructor = (mark, view, inline) => {
252
+ const HTMLAttributes = getRenderedAttributes(mark, extensionAttributes)
253
+
254
+ return addMarkView()({
255
+ // pass-through
256
+ mark,
257
+ view,
258
+ inline,
259
+ // tiptap-specific
260
+ editor,
261
+ extension,
262
+ HTMLAttributes,
263
+ })
264
+ }
265
+
266
+ return [extension.name, markView]
267
+ }),
268
+ )
269
+ }
270
+
320
271
  /**
321
272
  * Go through all extensions, create extension storages & setup marks
322
273
  * & bind editor event listener.
323
274
  */
324
275
  private setupExtensions() {
325
- this.extensions.forEach(extension => {
326
- // store extension storage in editor
327
- this.editor.extensionStorage[extension.name] = extension.storage
276
+ const extensions = this.extensions
277
+ // re-initialize the extension storage object instance
278
+ this.editor.extensionStorage = Object.fromEntries(
279
+ extensions.map(extension => [extension.name, extension.storage]),
280
+ ) as unknown as Storage
328
281
 
282
+ extensions.forEach(extension => {
329
283
  const context = {
330
284
  name: extension.name,
331
285
  options: extension.options,
332
- storage: extension.storage,
286
+ storage: this.editor.extensionStorage[extension.name as keyof Storage],
333
287
  editor: this.editor,
334
288
  type: getSchemaTypeByName(extension.name, this.schema),
335
289
  }
@@ -342,11 +296,7 @@ export class ExtensionManager {
342
296
  }
343
297
  }
344
298
 
345
- const onBeforeCreate = getExtensionField<AnyConfig['onBeforeCreate']>(
346
- extension,
347
- 'onBeforeCreate',
348
- context,
349
- )
299
+ const onBeforeCreate = getExtensionField<AnyConfig['onBeforeCreate']>(extension, 'onBeforeCreate', context)
350
300
  const onCreate = getExtensionField<AnyConfig['onCreate']>(extension, 'onCreate', context)
351
301
  const onUpdate = getExtensionField<AnyConfig['onUpdate']>(extension, 'onUpdate', context)
352
302
  const onSelectionUpdate = getExtensionField<AnyConfig['onSelectionUpdate']>(
@@ -354,11 +304,7 @@ export class ExtensionManager {
354
304
  'onSelectionUpdate',
355
305
  context,
356
306
  )
357
- const onTransaction = getExtensionField<AnyConfig['onTransaction']>(
358
- extension,
359
- 'onTransaction',
360
- context,
361
- )
307
+ const onTransaction = getExtensionField<AnyConfig['onTransaction']>(extension, 'onTransaction', context)
362
308
  const onFocus = getExtensionField<AnyConfig['onFocus']>(extension, 'onFocus', context)
363
309
  const onBlur = getExtensionField<AnyConfig['onBlur']>(extension, 'onBlur', context)
364
310
  const onDestroy = getExtensionField<AnyConfig['onDestroy']>(extension, 'onDestroy', context)
package/src/InputRule.ts CHANGED
@@ -6,57 +6,48 @@ import { Editor } from './Editor.js'
6
6
  import { createChainableState } from './helpers/createChainableState.js'
7
7
  import { getHTMLFromFragment } from './helpers/getHTMLFromFragment.js'
8
8
  import { getTextContentFromNodes } from './helpers/getTextContentFromNodes.js'
9
- import {
10
- CanCommands,
11
- ChainedCommands,
12
- ExtendedRegExpMatchArray,
13
- Range,
14
- SingleCommands,
15
- } from './types.js'
9
+ import { CanCommands, ChainedCommands, ExtendedRegExpMatchArray, Range, SingleCommands } from './types.js'
16
10
  import { isRegExp } from './utilities/isRegExp.js'
17
11
 
18
12
  export type InputRuleMatch = {
19
- index: number;
20
- text: string;
21
- replaceWith?: string;
22
- match?: RegExpMatchArray;
23
- data?: Record<string, any>;
24
- };
13
+ index: number
14
+ text: string
15
+ replaceWith?: string
16
+ match?: RegExpMatchArray
17
+ data?: Record<string, any>
18
+ }
25
19
 
26
- export type InputRuleFinder = RegExp | ((text: string) => InputRuleMatch | null);
20
+ export type InputRuleFinder = RegExp | ((text: string) => InputRuleMatch | null)
27
21
 
28
22
  export class InputRule {
29
23
  find: InputRuleFinder
30
24
 
31
25
  handler: (props: {
32
- state: EditorState;
33
- range: Range;
34
- match: ExtendedRegExpMatchArray;
35
- commands: SingleCommands;
36
- chain: () => ChainedCommands;
37
- can: () => CanCommands;
26
+ state: EditorState
27
+ range: Range
28
+ match: ExtendedRegExpMatchArray
29
+ commands: SingleCommands
30
+ chain: () => ChainedCommands
31
+ can: () => CanCommands
38
32
  }) => void | null
39
33
 
40
34
  constructor(config: {
41
- find: InputRuleFinder;
35
+ find: InputRuleFinder
42
36
  handler: (props: {
43
- state: EditorState;
44
- range: Range;
45
- match: ExtendedRegExpMatchArray;
46
- commands: SingleCommands;
47
- chain: () => ChainedCommands;
48
- can: () => CanCommands;
49
- }) => void | null;
37
+ state: EditorState
38
+ range: Range
39
+ match: ExtendedRegExpMatchArray
40
+ commands: SingleCommands
41
+ chain: () => ChainedCommands
42
+ can: () => CanCommands
43
+ }) => void | null
50
44
  }) {
51
45
  this.find = config.find
52
46
  this.handler = config.handler
53
47
  }
54
48
  }
55
49
 
56
- const inputRuleMatcherHandler = (
57
- text: string,
58
- find: InputRuleFinder,
59
- ): ExtendedRegExpMatchArray | null => {
50
+ const inputRuleMatcherHandler = (text: string, find: InputRuleFinder): ExtendedRegExpMatchArray | null => {
60
51
  if (isRegExp(find)) {
61
52
  return find.exec(text)
62
53
  }
@@ -75,9 +66,7 @@ const inputRuleMatcherHandler = (
75
66
 
76
67
  if (inputRuleMatch.replaceWith) {
77
68
  if (!inputRuleMatch.text.includes(inputRuleMatch.replaceWith)) {
78
- console.warn(
79
- '[tiptap warn]: "inputRuleMatch.replaceWith" must be part of "inputRuleMatch.text".',
80
- )
69
+ console.warn('[tiptap warn]: "inputRuleMatch.replaceWith" must be part of "inputRuleMatch.text".')
81
70
  }
82
71
 
83
72
  result.push(inputRuleMatch.replaceWith)
@@ -87,16 +76,14 @@ const inputRuleMatcherHandler = (
87
76
  }
88
77
 
89
78
  function run(config: {
90
- editor: Editor;
91
- from: number;
92
- to: number;
93
- text: string;
94
- rules: InputRule[];
95
- plugin: Plugin;
79
+ editor: Editor
80
+ from: number
81
+ to: number
82
+ text: string
83
+ rules: InputRule[]
84
+ plugin: Plugin
96
85
  }): boolean {
97
- const {
98
- editor, from, to, text, rules, plugin,
99
- } = config
86
+ const { editor, from, to, text, rules, plugin } = config
100
87
  const { view } = editor
101
88
 
102
89
  if (view.composing) {
@@ -107,9 +94,9 @@ function run(config: {
107
94
 
108
95
  if (
109
96
  // check for code node
110
- $from.parent.type.spec.code
97
+ $from.parent.type.spec.code ||
111
98
  // check for code mark
112
- || !!($from.nodeBefore || $from.nodeAfter)?.marks.find(mark => mark.type.spec.code)
99
+ !!($from.nodeBefore || $from.nodeAfter)?.marks.find(mark => mark.type.spec.code)
113
100
  ) {
114
101
  return false
115
102
  }
@@ -197,8 +184,8 @@ export function inputRulesPlugin(props: { editor: Editor; rules: InputRule[] }):
197
184
  const simulatedInputMeta = tr.getMeta('applyInputRules') as
198
185
  | undefined
199
186
  | {
200
- from: number;
201
- text: string | ProseMirrorNode | Fragment;
187
+ from: number
188
+ text: string | ProseMirrorNode | Fragment
202
189
  }
203
190
  const isSimulatedInput = !!simulatedInputMeta
204
191