@blocknote/core 0.38.0 → 0.39.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/BlockNoteSchema-DmZ6UQfY.cjs +11 -0
- package/dist/BlockNoteSchema-DmZ6UQfY.cjs.map +1 -0
- package/dist/BlockNoteSchema-oR047ACf.js +4275 -0
- package/dist/BlockNoteSchema-oR047ACf.js.map +1 -0
- package/dist/blocknote.cjs +4 -12
- package/dist/blocknote.cjs.map +1 -1
- package/dist/blocknote.js +3401 -7305
- package/dist/blocknote.js.map +1 -1
- package/dist/blocks.cjs +2 -0
- package/dist/blocks.cjs.map +1 -0
- package/dist/blocks.js +71 -0
- package/dist/blocks.js.map +1 -0
- package/dist/style.css +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/dist/webpack-stats.json +1 -1
- package/package.json +19 -16
- package/src/api/blockManipulation/commands/insertBlocks/insertBlocks.ts +1 -1
- package/src/api/blockManipulation/commands/replaceBlocks/replaceBlocks.ts +2 -2
- package/src/api/blockManipulation/commands/splitBlock/splitBlock.ts +34 -25
- package/src/api/blockManipulation/setupTestEnv.ts +0 -1
- package/src/api/clipboard/fromClipboard/handleFileInsertion.ts +6 -10
- package/src/api/clipboard/fromClipboard/pasteExtension.ts +1 -1
- package/src/api/clipboard/toClipboard/copyExtension.ts +1 -1
- package/src/api/exporters/html/util/serializeBlocksExternalHTML.ts +128 -28
- package/src/api/exporters/html/util/serializeBlocksInternalHTML.ts +101 -41
- package/src/api/pmUtil.ts +1 -1
- package/src/api/positionMapping.test.ts +58 -15
- package/src/api/positionMapping.ts +2 -4
- package/src/blocks/Audio/block.ts +174 -0
- package/src/blocks/BlockNoteSchema.ts +59 -0
- package/src/blocks/Code/block.ts +303 -0
- package/src/blocks/Code/shiki.ts +73 -0
- package/src/blocks/File/block.ts +98 -0
- package/src/blocks/{FileBlockContent → File}/helpers/render/createAddFileButton.ts +5 -2
- package/src/blocks/{FileBlockContent → File}/helpers/render/createFileBlockWrapper.ts +15 -6
- package/src/blocks/{FileBlockContent → File}/helpers/render/createFileNameWithIcon.ts +15 -2
- package/src/blocks/{FileBlockContent → File}/helpers/render/createResizableFileBlockWrapper.ts +21 -2
- package/src/blocks/Heading/block.ts +138 -0
- package/src/blocks/Image/block.ts +190 -0
- package/src/blocks/ListItem/BulletListItem/block.ts +116 -0
- package/src/blocks/ListItem/CheckListItem/block.ts +175 -0
- package/src/blocks/ListItem/NumberedListItem/IndexingPlugin.ts +173 -0
- package/src/blocks/ListItem/NumberedListItem/block.ts +133 -0
- package/src/blocks/ListItem/ToggleListItem/block.ts +78 -0
- package/src/blocks/PageBreak/block.ts +72 -0
- package/src/blocks/{PageBreakBlockContent → PageBreak}/getPageBreakSlashMenuItems.ts +9 -7
- package/src/blocks/Paragraph/block.ts +80 -0
- package/src/blocks/Quote/block.ts +90 -0
- package/src/blocks/{TableBlockContent/TableBlockContent.ts → Table/block.ts} +169 -51
- package/src/blocks/ToggleWrapper/createToggleWrapper.ts +1 -1
- package/src/blocks/Video/block.ts +143 -0
- package/src/blocks/defaultBlockHelpers.ts +2 -2
- package/src/blocks/defaultBlockTypeGuards.ts +143 -174
- package/src/blocks/defaultBlocks.ts +107 -35
- package/src/blocks/defaultProps.ts +145 -4
- package/src/blocks/index.ts +26 -0
- package/src/blocks/utils/listItemEnterHandler.ts +42 -0
- package/src/editor/Block.css +54 -18
- package/src/editor/BlockNoteEditor.ts +256 -211
- package/src/editor/BlockNoteExtension.ts +92 -0
- package/src/editor/BlockNoteExtensions.ts +18 -17
- package/src/editor/defaultColors.ts +2 -2
- package/src/exporter/Exporter.ts +1 -1
- package/src/exporter/mapping.ts +1 -1
- package/src/extensions/BackgroundColor/BackgroundColorExtension.ts +3 -20
- package/src/extensions/BackgroundColor/BackgroundColorMark.ts +6 -8
- package/src/extensions/BlockChange/BlockChangePlugin.ts +2 -1
- package/src/extensions/Collaboration/__snapshots__/fork-yjs-snap-editor-forked.json +2 -2
- package/src/extensions/Collaboration/__snapshots__/fork-yjs-snap-editor.json +2 -2
- package/src/extensions/Collaboration/__snapshots__/fork-yjs-snap-forked.html +1 -1
- package/src/extensions/Collaboration/__snapshots__/fork-yjs-snap.html +1 -1
- package/src/extensions/Collaboration/schemaMigration/SchemaMigrationPlugin.ts +52 -0
- package/src/extensions/Collaboration/schemaMigration/migrationRules/index.ts +4 -0
- package/src/extensions/Collaboration/schemaMigration/migrationRules/migrationRule.ts +4 -0
- package/src/extensions/Collaboration/schemaMigration/migrationRules/moveColorAttributes.ts +78 -0
- package/src/extensions/Comments/CommentsPlugin.ts +1 -1
- package/src/extensions/FilePanel/FilePanelPlugin.ts +5 -10
- package/src/extensions/FormattingToolbar/FormattingToolbarPlugin.ts +1 -1
- package/src/extensions/KeyboardShortcuts/KeyboardShortcutsExtension.ts +4 -3
- package/src/extensions/Placeholder/PlaceholderPlugin.ts +6 -6
- package/src/extensions/PreviousBlockType/PreviousBlockTypePlugin.ts +1 -23
- package/src/extensions/SideMenu/SideMenuPlugin.ts +1 -3
- package/src/extensions/SideMenu/dragging.ts +2 -2
- package/src/extensions/SuggestionMenu/SuggestionPlugin.ts +4 -7
- package/src/extensions/SuggestionMenu/getDefaultEmojiPickerItems.ts +6 -2
- package/src/extensions/SuggestionMenu/getDefaultSlashMenuItems.ts +24 -17
- package/src/extensions/TableHandles/TableHandlesPlugin.ts +8 -8
- package/src/extensions/TextAlignment/TextAlignmentExtension.ts +5 -11
- package/src/extensions/TextColor/TextColorExtension.ts +3 -17
- package/src/extensions/TextColor/TextColorMark.ts +4 -9
- package/src/extensions/UniqueID/UniqueID.ts +6 -13
- package/src/index.ts +2 -28
- package/src/schema/blocks/createSpec.ts +342 -169
- package/src/schema/blocks/internal.ts +77 -138
- package/src/schema/blocks/types.ts +264 -94
- package/src/schema/index.ts +1 -0
- package/src/schema/inlineContent/createSpec.ts +99 -21
- package/src/schema/inlineContent/internal.ts +16 -7
- package/src/schema/inlineContent/types.ts +24 -2
- package/src/schema/propTypes.ts +15 -9
- package/src/schema/schema.ts +209 -0
- package/src/schema/styles/createSpec.ts +79 -31
- package/src/schema/styles/internal.ts +61 -2
- package/src/schema/styles/types.ts +17 -3
- package/src/util/topo-sort.test.ts +125 -0
- package/src/util/topo-sort.ts +160 -0
- package/types/src/api/blockManipulation/commands/splitBlock/splitBlock.d.ts +2 -1
- package/types/src/api/blockManipulation/selections/selection.d.ts +1 -1
- package/types/src/api/blockManipulation/setupTestEnv.d.ts +29 -543
- package/types/src/api/exporters/html/util/serializeBlocksExternalHTML.d.ts +1 -1
- package/types/src/api/exporters/html/util/serializeBlocksInternalHTML.d.ts +1 -1
- package/types/src/api/pmUtil.d.ts +1 -1
- package/types/src/blocks/Audio/block.d.ts +58 -0
- package/types/src/blocks/BlockNoteSchema.d.ts +18 -0
- package/types/src/blocks/{CodeBlockContent/CodeBlockContent.d.ts → Code/block.d.ts} +25 -26
- package/types/src/blocks/Code/shiki.d.ts +4 -0
- package/types/src/blocks/File/block.d.ts +37 -0
- package/types/src/blocks/File/helpers/render/createAddFileButton.d.ts +6 -0
- package/types/src/blocks/File/helpers/render/createFileBlockWrapper.d.ts +25 -0
- package/types/src/blocks/{FileBlockContent → File}/helpers/render/createFileNameWithIcon.d.ts +6 -2
- package/types/src/blocks/File/helpers/render/createResizableFileBlockWrapper.d.ts +31 -0
- package/types/src/blocks/Heading/block.d.ts +71 -0
- package/types/src/blocks/Image/block.d.ts +102 -0
- package/types/src/blocks/ListItem/BulletListItem/block.d.ts +25 -0
- package/types/src/blocks/ListItem/CheckListItem/block.d.ts +33 -0
- package/types/src/blocks/ListItem/NumberedListItem/IndexingPlugin.d.ts +8 -0
- package/types/src/blocks/ListItem/NumberedListItem/block.d.ts +33 -0
- package/types/src/blocks/ListItem/ToggleListItem/block.d.ts +25 -0
- package/types/src/blocks/PageBreak/block.d.ts +11 -0
- package/types/src/blocks/{PageBreakBlockContent → PageBreak}/getPageBreakSlashMenuItems.d.ts +4 -2
- package/types/src/blocks/Paragraph/block.d.ts +25 -0
- package/types/src/blocks/Quote/block.d.ts +17 -0
- package/types/src/blocks/Table/block.d.ts +21 -0
- package/types/src/blocks/Video/block.d.ts +67 -0
- package/types/src/blocks/defaultBlockHelpers.d.ts +1 -1
- package/types/src/blocks/defaultBlockTypeGuards.d.ts +15 -36
- package/types/src/blocks/defaultBlocks.d.ts +221 -1060
- package/types/src/blocks/defaultProps.d.ts +17 -1
- package/types/src/blocks/index.d.ts +24 -0
- package/types/src/blocks/utils/listItemEnterHandler.d.ts +2 -0
- package/types/src/editor/BlockNoteEditor.d.ts +36 -67
- package/types/src/editor/BlockNoteExtension.d.ts +67 -0
- package/types/src/editor/BlockNoteExtensions.d.ts +1 -1
- package/types/src/editor/defaultColors.d.ts +8 -76
- package/types/src/exporter/Exporter.d.ts +1 -1
- package/types/src/exporter/mapping.d.ts +1 -1
- package/types/src/extensions/BackgroundColor/BackgroundColorMark.d.ts +4 -1
- package/types/src/extensions/Collaboration/schemaMigration/SchemaMigrationPlugin.d.ts +7 -0
- package/types/src/extensions/Collaboration/schemaMigration/migrationRules/index.d.ts +3 -0
- package/types/src/extensions/Collaboration/schemaMigration/migrationRules/migrationRule.d.ts +3 -0
- package/types/src/extensions/Collaboration/schemaMigration/migrationRules/moveColorAttributes.d.ts +2 -0
- package/types/src/extensions/Comments/CommentsPlugin.d.ts +1 -1
- package/types/src/extensions/FilePanel/FilePanelPlugin.d.ts +4 -4
- package/types/src/extensions/TextColor/TextColorMark.d.ts +4 -1
- package/types/src/index.d.ts +2 -25
- package/types/src/schema/blocks/createSpec.d.ts +16 -36
- package/types/src/schema/blocks/internal.d.ts +11 -33
- package/types/src/schema/blocks/types.d.ts +181 -57
- package/types/src/schema/index.d.ts +1 -0
- package/types/src/schema/inlineContent/createSpec.d.ts +36 -2
- package/types/src/schema/inlineContent/internal.d.ts +7 -15
- package/types/src/schema/inlineContent/types.d.ts +15 -1
- package/types/src/schema/propTypes.d.ts +4 -4
- package/types/src/schema/schema.d.ts +40 -0
- package/types/src/schema/styles/createSpec.d.ts +6 -4
- package/types/src/schema/styles/internal.d.ts +6 -3
- package/types/src/schema/styles/types.d.ts +11 -2
- package/types/src/util/topo-sort.d.ts +18 -0
- package/types/src/util/topo-sort.test.d.ts +1 -0
- package/src/blocks/AudioBlockContent/AudioBlockContent.ts +0 -144
- package/src/blocks/CodeBlockContent/CodeBlockContent.ts +0 -445
- package/src/blocks/FileBlockContent/FileBlockContent.ts +0 -100
- package/src/blocks/HeadingBlockContent/HeadingBlockContent.ts +0 -159
- package/src/blocks/ImageBlockContent/ImageBlockContent.ts +0 -159
- package/src/blocks/ListItemBlockContent/BulletListItemBlockContent/BulletListItemBlockContent.ts +0 -134
- package/src/blocks/ListItemBlockContent/CheckListItemBlockContent/CheckListItemBlockContent.ts +0 -299
- package/src/blocks/ListItemBlockContent/NumberedListItemBlockContent/NumberedListIndexingPlugin.ts +0 -86
- package/src/blocks/ListItemBlockContent/NumberedListItemBlockContent/NumberedListItemBlockContent.ts +0 -172
- package/src/blocks/ListItemBlockContent/ToggleListItemBlockContent/ToggleListItemBlockContent.ts +0 -104
- package/src/blocks/PageBreakBlockContent/PageBreakBlockContent.ts +0 -49
- package/src/blocks/PageBreakBlockContent/schema.ts +0 -40
- package/src/blocks/ParagraphBlockContent/ParagraphBlockContent.ts +0 -78
- package/src/blocks/QuoteBlockContent/QuoteBlockContent.ts +0 -121
- package/src/blocks/VideoBlockContent/VideoBlockContent.ts +0 -158
- package/src/editor/BlockNoteSchema.ts +0 -107
- package/src/editor/BlockNoteTipTapEditor.ts +0 -335
- package/types/src/blocks/AudioBlockContent/AudioBlockContent.d.ts +0 -99
- package/types/src/blocks/FileBlockContent/FileBlockContent.d.ts +0 -90
- package/types/src/blocks/FileBlockContent/helpers/render/createAddFileButton.d.ts +0 -6
- package/types/src/blocks/FileBlockContent/helpers/render/createFileBlockWrapper.d.ts +0 -9
- package/types/src/blocks/FileBlockContent/helpers/render/createResizableFileBlockWrapper.d.ts +0 -9
- package/types/src/blocks/HeadingBlockContent/HeadingBlockContent.d.ts +0 -67
- package/types/src/blocks/ImageBlockContent/ImageBlockContent.d.ts +0 -131
- package/types/src/blocks/ListItemBlockContent/BulletListItemBlockContent/BulletListItemBlockContent.d.ts +0 -46
- package/types/src/blocks/ListItemBlockContent/CheckListItemBlockContent/CheckListItemBlockContent.d.ts +0 -55
- package/types/src/blocks/ListItemBlockContent/NumberedListItemBlockContent/NumberedListIndexingPlugin.d.ts +0 -2
- package/types/src/blocks/ListItemBlockContent/NumberedListItemBlockContent/NumberedListItemBlockContent.d.ts +0 -58
- package/types/src/blocks/ListItemBlockContent/ToggleListItemBlockContent/ToggleListItemBlockContent.d.ts +0 -46
- package/types/src/blocks/PageBreakBlockContent/PageBreakBlockContent.d.ts +0 -31
- package/types/src/blocks/PageBreakBlockContent/schema.d.ts +0 -86
- package/types/src/blocks/ParagraphBlockContent/ParagraphBlockContent.d.ts +0 -52
- package/types/src/blocks/QuoteBlockContent/QuoteBlockContent.d.ts +0 -52
- package/types/src/blocks/TableBlockContent/TableBlockContent.d.ts +0 -39
- package/types/src/blocks/VideoBlockContent/VideoBlockContent.d.ts +0 -131
- package/types/src/editor/BlockNoteSchema.d.ts +0 -34
- package/types/src/editor/BlockNoteTipTapEditor.d.ts +0 -43
- /package/src/blocks/{AudioBlockContent → Audio}/parseAudioElement.ts +0 -0
- /package/src/blocks/{FileBlockContent → File}/helpers/parse/parseEmbedElement.ts +0 -0
- /package/src/blocks/{FileBlockContent → File}/helpers/parse/parseFigureElement.ts +0 -0
- /package/src/blocks/{FileBlockContent → File}/helpers/toExternalHTML/createFigureWithCaption.ts +0 -0
- /package/src/blocks/{FileBlockContent → File}/helpers/toExternalHTML/createLinkWithCaption.ts +0 -0
- /package/src/blocks/{FileBlockContent → File/helpers}/uploadToTmpFilesDotOrg_DEV_ONLY.ts +0 -0
- /package/src/blocks/{ImageBlockContent → Image}/parseImageElement.ts +0 -0
- /package/src/blocks/{ListItemBlockContent → ListItem}/ListItemKeyboardShortcuts.ts +0 -0
- /package/src/blocks/{ListItemBlockContent → ListItem}/getListItemContent.ts +0 -0
- /package/src/blocks/{TableBlockContent → Table}/TableExtension.ts +0 -0
- /package/src/blocks/{VideoBlockContent → Video}/parseVideoElement.ts +0 -0
- /package/types/src/blocks/{AudioBlockContent → Audio}/parseAudioElement.d.ts +0 -0
- /package/types/src/blocks/{FileBlockContent → File}/helpers/parse/parseEmbedElement.d.ts +0 -0
- /package/types/src/blocks/{FileBlockContent → File}/helpers/parse/parseFigureElement.d.ts +0 -0
- /package/types/src/blocks/{FileBlockContent → File}/helpers/toExternalHTML/createFigureWithCaption.d.ts +0 -0
- /package/types/src/blocks/{FileBlockContent → File}/helpers/toExternalHTML/createLinkWithCaption.d.ts +0 -0
- /package/types/src/blocks/{FileBlockContent → File/helpers}/uploadToTmpFilesDotOrg_DEV_ONLY.d.ts +0 -0
- /package/types/src/blocks/{ImageBlockContent → Image}/parseImageElement.d.ts +0 -0
- /package/types/src/blocks/{ListItemBlockContent → ListItem}/ListItemKeyboardShortcuts.d.ts +0 -0
- /package/types/src/blocks/{ListItemBlockContent → ListItem}/getListItemContent.d.ts +0 -0
- /package/types/src/blocks/{TableBlockContent → Table}/TableExtension.d.ts +0 -0
- /package/types/src/blocks/{VideoBlockContent → Video}/parseVideoElement.d.ts +0 -0
|
@@ -0,0 +1,173 @@
|
|
|
1
|
+
import type { Node } from "@tiptap/pm/model";
|
|
2
|
+
import type { Transaction } from "@tiptap/pm/state";
|
|
3
|
+
import { Plugin, PluginKey } from "@tiptap/pm/state";
|
|
4
|
+
import { Decoration, DecorationSet } from "@tiptap/pm/view";
|
|
5
|
+
|
|
6
|
+
import { getBlockInfo } from "../../../api/getBlockInfoFromPos.js";
|
|
7
|
+
|
|
8
|
+
// Loosely based on https://github.com/ueberdosis/tiptap/blob/7ac01ef0b816a535e903b5ca92492bff110a71ae/packages/extension-mathematics/src/MathematicsPlugin.ts (MIT)
|
|
9
|
+
|
|
10
|
+
type DecoSpec = {
|
|
11
|
+
index: number;
|
|
12
|
+
isFirst: boolean;
|
|
13
|
+
hasStart: boolean;
|
|
14
|
+
side: number;
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
type Deco = Omit<Decoration, "spec"> & { spec: DecoSpec };
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* Calculate the index for a numbered list item based on its position and previous siblings
|
|
21
|
+
*/
|
|
22
|
+
function calculateListItemIndex(
|
|
23
|
+
node: Node,
|
|
24
|
+
pos: number,
|
|
25
|
+
tr: Transaction,
|
|
26
|
+
map: Map<Node, number>,
|
|
27
|
+
): { index: number; isFirst: boolean; hasStart: boolean } {
|
|
28
|
+
let index: number = node.firstChild!.attrs["start"] || 1;
|
|
29
|
+
let isFirst = true;
|
|
30
|
+
const hasStart = !!node.firstChild!.attrs["start"];
|
|
31
|
+
|
|
32
|
+
const blockInfo = getBlockInfo({
|
|
33
|
+
posBeforeNode: pos,
|
|
34
|
+
node,
|
|
35
|
+
});
|
|
36
|
+
|
|
37
|
+
if (!blockInfo.isBlockContainer) {
|
|
38
|
+
throw new Error("impossible");
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
// Check if this block is the start of a new ordered list
|
|
42
|
+
const prevBlock = tr.doc.resolve(blockInfo.bnBlock.beforePos).nodeBefore;
|
|
43
|
+
const prevBlockIndex = prevBlock ? map.get(prevBlock) : undefined;
|
|
44
|
+
|
|
45
|
+
if (prevBlockIndex !== undefined) {
|
|
46
|
+
index = prevBlockIndex + 1;
|
|
47
|
+
isFirst = false;
|
|
48
|
+
} else if (prevBlock) {
|
|
49
|
+
// Because we only check the affected ranges, we may need to walk backwards to find the previous block's index
|
|
50
|
+
// We can't just rely on the map, because the map is reset every `apply` call
|
|
51
|
+
const prevBlockInfo = getBlockInfo({
|
|
52
|
+
posBeforeNode: blockInfo.bnBlock.beforePos - prevBlock.nodeSize,
|
|
53
|
+
node: prevBlock,
|
|
54
|
+
});
|
|
55
|
+
|
|
56
|
+
const isPrevBlockOrderedListItem =
|
|
57
|
+
prevBlockInfo.blockNoteType === "numberedListItem";
|
|
58
|
+
if (isPrevBlockOrderedListItem) {
|
|
59
|
+
// recurse to get the index of the previous block
|
|
60
|
+
const itemIndex = calculateListItemIndex(
|
|
61
|
+
prevBlock,
|
|
62
|
+
blockInfo.bnBlock.beforePos - prevBlock.nodeSize,
|
|
63
|
+
tr,
|
|
64
|
+
map,
|
|
65
|
+
);
|
|
66
|
+
index = itemIndex.index + 1;
|
|
67
|
+
isFirst = false;
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
// Note: we set the map late, so that when we recurse, we can rely on the map to get the previous block's index in one lookup
|
|
71
|
+
map.set(node, index);
|
|
72
|
+
|
|
73
|
+
return { index, isFirst, hasStart };
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/**
|
|
77
|
+
* Get the decorations for the current state based on the previous state,
|
|
78
|
+
* and the transaction that was applied to get to the current state
|
|
79
|
+
*/
|
|
80
|
+
function getDecorations(
|
|
81
|
+
tr: Transaction,
|
|
82
|
+
previousPluginState: { decorations: DecorationSet },
|
|
83
|
+
) {
|
|
84
|
+
const map = new Map<Node, number>();
|
|
85
|
+
|
|
86
|
+
const nextDecorationSet = previousPluginState.decorations.map(
|
|
87
|
+
tr.mapping,
|
|
88
|
+
tr.doc,
|
|
89
|
+
);
|
|
90
|
+
const decorationsToAdd = [] as Deco[];
|
|
91
|
+
|
|
92
|
+
tr.doc.nodesBetween(0, tr.doc.nodeSize - 2, (node, pos) => {
|
|
93
|
+
if (
|
|
94
|
+
node.type.name === "blockContainer" &&
|
|
95
|
+
node.firstChild!.type.name === "numberedListItem"
|
|
96
|
+
) {
|
|
97
|
+
const { index, isFirst, hasStart } = calculateListItemIndex(
|
|
98
|
+
node,
|
|
99
|
+
pos,
|
|
100
|
+
tr,
|
|
101
|
+
map,
|
|
102
|
+
);
|
|
103
|
+
|
|
104
|
+
// Check if decoration already exists with the same properties (for perf reasons)
|
|
105
|
+
const existingDecorations = nextDecorationSet.find(
|
|
106
|
+
pos,
|
|
107
|
+
pos + node.nodeSize,
|
|
108
|
+
(deco: DecoSpec) =>
|
|
109
|
+
deco.index === index &&
|
|
110
|
+
deco.isFirst === isFirst &&
|
|
111
|
+
deco.hasStart === hasStart,
|
|
112
|
+
);
|
|
113
|
+
|
|
114
|
+
if (existingDecorations.length === 0) {
|
|
115
|
+
// Create a widget decoration to display the index
|
|
116
|
+
decorationsToAdd.push(
|
|
117
|
+
// move in by 1 to account for the block container
|
|
118
|
+
Decoration.node(pos + 1, pos + node.nodeSize - 1, {
|
|
119
|
+
"data-index": index.toString(),
|
|
120
|
+
}),
|
|
121
|
+
);
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
});
|
|
125
|
+
|
|
126
|
+
// Remove any decorations that exist at the same position, they will be replaced by the new decorations
|
|
127
|
+
const decorationsToRemove = decorationsToAdd.flatMap((deco) =>
|
|
128
|
+
nextDecorationSet.find(deco.from, deco.to),
|
|
129
|
+
);
|
|
130
|
+
|
|
131
|
+
return {
|
|
132
|
+
decorations: nextDecorationSet
|
|
133
|
+
// Remove existing decorations that are going to be replaced
|
|
134
|
+
.remove(decorationsToRemove)
|
|
135
|
+
// Add any new decorations
|
|
136
|
+
.add(tr.doc, decorationsToAdd),
|
|
137
|
+
};
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
/**
|
|
141
|
+
* This plugin adds decorations to numbered list items to display their index.
|
|
142
|
+
*/
|
|
143
|
+
export const NumberedListIndexingDecorationPlugin = () => {
|
|
144
|
+
return new Plugin<{ decorations: DecorationSet }>({
|
|
145
|
+
key: new PluginKey("numbered-list-indexing-decorations"),
|
|
146
|
+
|
|
147
|
+
state: {
|
|
148
|
+
init(_config, state) {
|
|
149
|
+
// We create an empty transaction to get the decorations for the initial state based on the initial content
|
|
150
|
+
return getDecorations(state.tr, {
|
|
151
|
+
decorations: DecorationSet.empty,
|
|
152
|
+
});
|
|
153
|
+
},
|
|
154
|
+
apply(tr, previousPluginState) {
|
|
155
|
+
if (
|
|
156
|
+
!tr.docChanged &&
|
|
157
|
+
!tr.selectionSet &&
|
|
158
|
+
previousPluginState.decorations
|
|
159
|
+
) {
|
|
160
|
+
// Just reuse the existing decorations, since nothing should have changed
|
|
161
|
+
return previousPluginState;
|
|
162
|
+
}
|
|
163
|
+
return getDecorations(tr, previousPluginState);
|
|
164
|
+
},
|
|
165
|
+
},
|
|
166
|
+
|
|
167
|
+
props: {
|
|
168
|
+
decorations(state) {
|
|
169
|
+
return this.getState(state)?.decorations ?? DecorationSet.empty;
|
|
170
|
+
},
|
|
171
|
+
},
|
|
172
|
+
});
|
|
173
|
+
};
|
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
import { createBlockNoteExtension } from "../../../editor/BlockNoteExtension.js";
|
|
2
|
+
import { createBlockConfig, createBlockSpec } from "../../../schema/index.js";
|
|
3
|
+
import {
|
|
4
|
+
addDefaultPropsExternalHTML,
|
|
5
|
+
defaultProps,
|
|
6
|
+
parseDefaultProps,
|
|
7
|
+
} from "../../defaultProps.js";
|
|
8
|
+
import { handleEnter } from "../../utils/listItemEnterHandler.js";
|
|
9
|
+
import { getListItemContent } from "../getListItemContent.js";
|
|
10
|
+
import { NumberedListIndexingDecorationPlugin } from "./IndexingPlugin.js";
|
|
11
|
+
|
|
12
|
+
export type NumberedListItemBlockConfig = ReturnType<
|
|
13
|
+
typeof createNumberedListItemBlockConfig
|
|
14
|
+
>;
|
|
15
|
+
|
|
16
|
+
export const createNumberedListItemBlockConfig = createBlockConfig(
|
|
17
|
+
() =>
|
|
18
|
+
({
|
|
19
|
+
type: "numberedListItem" as const,
|
|
20
|
+
propSchema: {
|
|
21
|
+
...defaultProps,
|
|
22
|
+
start: { default: undefined, type: "number" } as const,
|
|
23
|
+
},
|
|
24
|
+
content: "inline",
|
|
25
|
+
}) as const,
|
|
26
|
+
);
|
|
27
|
+
|
|
28
|
+
export const createNumberedListItemBlockSpec = createBlockSpec(
|
|
29
|
+
createNumberedListItemBlockConfig,
|
|
30
|
+
{
|
|
31
|
+
meta: {
|
|
32
|
+
isolating: false,
|
|
33
|
+
},
|
|
34
|
+
parse(element) {
|
|
35
|
+
if (element.tagName !== "LI") {
|
|
36
|
+
return undefined;
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
const parent = element.parentElement;
|
|
40
|
+
|
|
41
|
+
if (parent === null) {
|
|
42
|
+
return undefined;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
if (
|
|
46
|
+
parent.tagName === "OL" ||
|
|
47
|
+
(parent.tagName === "DIV" && parent.parentElement?.tagName === "OL")
|
|
48
|
+
) {
|
|
49
|
+
const startIndex = parseInt(parent.getAttribute("start") || "1");
|
|
50
|
+
|
|
51
|
+
const defaultProps = parseDefaultProps(element);
|
|
52
|
+
|
|
53
|
+
if (element.previousElementSibling || startIndex === 1) {
|
|
54
|
+
return defaultProps;
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
return {
|
|
58
|
+
...defaultProps,
|
|
59
|
+
start: startIndex,
|
|
60
|
+
};
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
return undefined;
|
|
64
|
+
},
|
|
65
|
+
// As `li` elements can contain multiple paragraphs, we need to merge their contents
|
|
66
|
+
// into a single one so that ProseMirror can parse everything correctly.
|
|
67
|
+
parseContent: ({ el, schema }) =>
|
|
68
|
+
getListItemContent(el, schema, "numberedListItem"),
|
|
69
|
+
render() {
|
|
70
|
+
// We use a <p> tag, because for <li> tags we'd need a <ul> element to put
|
|
71
|
+
// them in to be semantically correct, which we can't have due to the
|
|
72
|
+
// schema.
|
|
73
|
+
const dom = document.createElement("p");
|
|
74
|
+
|
|
75
|
+
return {
|
|
76
|
+
dom,
|
|
77
|
+
contentDOM: dom,
|
|
78
|
+
};
|
|
79
|
+
},
|
|
80
|
+
toExternalHTML(block) {
|
|
81
|
+
const li = document.createElement("li");
|
|
82
|
+
const p = document.createElement("p");
|
|
83
|
+
addDefaultPropsExternalHTML(block.props, li);
|
|
84
|
+
li.appendChild(p);
|
|
85
|
+
|
|
86
|
+
return {
|
|
87
|
+
dom: li,
|
|
88
|
+
contentDOM: p,
|
|
89
|
+
};
|
|
90
|
+
},
|
|
91
|
+
},
|
|
92
|
+
[
|
|
93
|
+
createBlockNoteExtension({
|
|
94
|
+
key: "numbered-list-item-shortcuts",
|
|
95
|
+
inputRules: [
|
|
96
|
+
{
|
|
97
|
+
find: new RegExp(`^(\\d+)\\.\\s$`),
|
|
98
|
+
replace({ match }) {
|
|
99
|
+
const start = parseInt(match[1]);
|
|
100
|
+
return {
|
|
101
|
+
type: "numberedListItem",
|
|
102
|
+
props: {
|
|
103
|
+
start: start !== 1 ? start : undefined,
|
|
104
|
+
},
|
|
105
|
+
};
|
|
106
|
+
},
|
|
107
|
+
},
|
|
108
|
+
],
|
|
109
|
+
keyboardShortcuts: {
|
|
110
|
+
Enter: ({ editor }) => {
|
|
111
|
+
return handleEnter(editor, "numberedListItem");
|
|
112
|
+
},
|
|
113
|
+
"Mod-Shift-7": ({ editor }) => {
|
|
114
|
+
const cursorPosition = editor.getTextCursorPosition();
|
|
115
|
+
|
|
116
|
+
if (
|
|
117
|
+
editor.schema.blockSchema[cursorPosition.block.type].content !==
|
|
118
|
+
"inline"
|
|
119
|
+
) {
|
|
120
|
+
return false;
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
editor.updateBlock(cursorPosition.block, {
|
|
124
|
+
type: "numberedListItem",
|
|
125
|
+
props: {},
|
|
126
|
+
});
|
|
127
|
+
return true;
|
|
128
|
+
},
|
|
129
|
+
},
|
|
130
|
+
plugins: [NumberedListIndexingDecorationPlugin()],
|
|
131
|
+
}),
|
|
132
|
+
],
|
|
133
|
+
);
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
import { createBlockNoteExtension } from "../../../editor/BlockNoteExtension.js";
|
|
2
|
+
import { createBlockConfig, createBlockSpec } from "../../../schema/index.js";
|
|
3
|
+
import {
|
|
4
|
+
addDefaultPropsExternalHTML,
|
|
5
|
+
defaultProps,
|
|
6
|
+
} from "../../defaultProps.js";
|
|
7
|
+
import { createToggleWrapper } from "../../ToggleWrapper/createToggleWrapper.js";
|
|
8
|
+
import { handleEnter } from "../../utils/listItemEnterHandler.js";
|
|
9
|
+
|
|
10
|
+
export type ToggleListItemBlockConfig = ReturnType<
|
|
11
|
+
typeof createToggleListItemBlockConfig
|
|
12
|
+
>;
|
|
13
|
+
|
|
14
|
+
export const createToggleListItemBlockConfig = createBlockConfig(
|
|
15
|
+
() =>
|
|
16
|
+
({
|
|
17
|
+
type: "toggleListItem" as const,
|
|
18
|
+
propSchema: {
|
|
19
|
+
...defaultProps,
|
|
20
|
+
},
|
|
21
|
+
content: "inline" as const,
|
|
22
|
+
}) as const,
|
|
23
|
+
);
|
|
24
|
+
|
|
25
|
+
export const createToggleListItemBlockSpec = createBlockSpec(
|
|
26
|
+
createToggleListItemBlockConfig,
|
|
27
|
+
{
|
|
28
|
+
meta: {
|
|
29
|
+
isolating: false,
|
|
30
|
+
},
|
|
31
|
+
render(block, editor) {
|
|
32
|
+
const paragraphEl = document.createElement("p");
|
|
33
|
+
const toggleWrapper = createToggleWrapper(
|
|
34
|
+
block as any,
|
|
35
|
+
editor,
|
|
36
|
+
paragraphEl,
|
|
37
|
+
);
|
|
38
|
+
return { ...toggleWrapper, contentDOM: paragraphEl };
|
|
39
|
+
},
|
|
40
|
+
toExternalHTML(block) {
|
|
41
|
+
const li = document.createElement("li");
|
|
42
|
+
const p = document.createElement("p");
|
|
43
|
+
addDefaultPropsExternalHTML(block.props, li);
|
|
44
|
+
li.appendChild(p);
|
|
45
|
+
|
|
46
|
+
return {
|
|
47
|
+
dom: li,
|
|
48
|
+
contentDOM: p,
|
|
49
|
+
};
|
|
50
|
+
},
|
|
51
|
+
},
|
|
52
|
+
[
|
|
53
|
+
createBlockNoteExtension({
|
|
54
|
+
key: "toggle-list-item-shortcuts",
|
|
55
|
+
keyboardShortcuts: {
|
|
56
|
+
Enter: ({ editor }) => {
|
|
57
|
+
return handleEnter(editor, "toggleListItem");
|
|
58
|
+
},
|
|
59
|
+
"Mod-Shift-6": ({ editor }) => {
|
|
60
|
+
const cursorPosition = editor.getTextCursorPosition();
|
|
61
|
+
|
|
62
|
+
if (
|
|
63
|
+
editor.schema.blockSchema[cursorPosition.block.type].content !==
|
|
64
|
+
"inline"
|
|
65
|
+
) {
|
|
66
|
+
return false;
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
editor.updateBlock(cursorPosition.block, {
|
|
70
|
+
type: "toggleListItem",
|
|
71
|
+
props: {},
|
|
72
|
+
});
|
|
73
|
+
return true;
|
|
74
|
+
},
|
|
75
|
+
},
|
|
76
|
+
}),
|
|
77
|
+
],
|
|
78
|
+
);
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import {
|
|
2
|
+
BlockSchema,
|
|
3
|
+
createBlockConfig,
|
|
4
|
+
createBlockSpec,
|
|
5
|
+
InlineContentSchema,
|
|
6
|
+
StyleSchema,
|
|
7
|
+
} from "../../schema/index.js";
|
|
8
|
+
import { BlockNoteSchema } from "../BlockNoteSchema.js";
|
|
9
|
+
|
|
10
|
+
export type PageBreakBlockConfig = ReturnType<
|
|
11
|
+
typeof createPageBreakBlockConfig
|
|
12
|
+
>;
|
|
13
|
+
|
|
14
|
+
export const createPageBreakBlockConfig = createBlockConfig(
|
|
15
|
+
() =>
|
|
16
|
+
({
|
|
17
|
+
type: "pageBreak" as const,
|
|
18
|
+
propSchema: {},
|
|
19
|
+
content: "none",
|
|
20
|
+
}) as const,
|
|
21
|
+
);
|
|
22
|
+
|
|
23
|
+
export const createPageBreakBlockSpec = createBlockSpec(
|
|
24
|
+
createPageBreakBlockConfig,
|
|
25
|
+
{
|
|
26
|
+
parse(element) {
|
|
27
|
+
if (
|
|
28
|
+
element.tagName === "DIV" &&
|
|
29
|
+
element.hasAttribute("data-page-break")
|
|
30
|
+
) {
|
|
31
|
+
return {};
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
return undefined;
|
|
35
|
+
},
|
|
36
|
+
render() {
|
|
37
|
+
const pageBreak = document.createElement("div");
|
|
38
|
+
|
|
39
|
+
pageBreak.setAttribute("data-page-break", "");
|
|
40
|
+
|
|
41
|
+
return {
|
|
42
|
+
dom: pageBreak,
|
|
43
|
+
};
|
|
44
|
+
},
|
|
45
|
+
toExternalHTML() {
|
|
46
|
+
const pageBreak = document.createElement("div");
|
|
47
|
+
|
|
48
|
+
pageBreak.setAttribute("data-page-break", "");
|
|
49
|
+
|
|
50
|
+
return {
|
|
51
|
+
dom: pageBreak,
|
|
52
|
+
};
|
|
53
|
+
},
|
|
54
|
+
},
|
|
55
|
+
);
|
|
56
|
+
|
|
57
|
+
/**
|
|
58
|
+
* Adds page break support to the given schema.
|
|
59
|
+
*/
|
|
60
|
+
export const withPageBreak = <
|
|
61
|
+
B extends BlockSchema,
|
|
62
|
+
I extends InlineContentSchema,
|
|
63
|
+
S extends StyleSchema,
|
|
64
|
+
>(
|
|
65
|
+
schema: BlockNoteSchema<B, I, S>,
|
|
66
|
+
) => {
|
|
67
|
+
return schema.extend({
|
|
68
|
+
blockSpecs: {
|
|
69
|
+
pageBreak: createPageBreakBlockSpec(),
|
|
70
|
+
},
|
|
71
|
+
});
|
|
72
|
+
};
|
|
@@ -6,19 +6,21 @@ import {
|
|
|
6
6
|
InlineContentSchema,
|
|
7
7
|
StyleSchema,
|
|
8
8
|
} from "../../schema/index.js";
|
|
9
|
-
import {
|
|
9
|
+
import { createPageBreakBlockConfig } from "./block.js";
|
|
10
10
|
|
|
11
11
|
export function checkPageBreakBlocksInSchema<
|
|
12
12
|
I extends InlineContentSchema,
|
|
13
13
|
S extends StyleSchema,
|
|
14
14
|
>(
|
|
15
15
|
editor: BlockNoteEditor<any, I, S>,
|
|
16
|
-
): editor is BlockNoteEditor<
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
16
|
+
): editor is BlockNoteEditor<
|
|
17
|
+
{
|
|
18
|
+
pageBreak: ReturnType<typeof createPageBreakBlockConfig>;
|
|
19
|
+
},
|
|
20
|
+
I,
|
|
21
|
+
S
|
|
22
|
+
> {
|
|
23
|
+
return "pageBreak" in editor.schema.blockSchema;
|
|
22
24
|
}
|
|
23
25
|
|
|
24
26
|
export function getPageBreakSlashMenuItems<
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import { createBlockNoteExtension } from "../../editor/BlockNoteExtension.js";
|
|
2
|
+
import { createBlockConfig, createBlockSpec } from "../../schema/index.js";
|
|
3
|
+
import {
|
|
4
|
+
addDefaultPropsExternalHTML,
|
|
5
|
+
defaultProps,
|
|
6
|
+
parseDefaultProps,
|
|
7
|
+
} from "../defaultProps.js";
|
|
8
|
+
|
|
9
|
+
export type ParagraphBlockConfig = ReturnType<
|
|
10
|
+
typeof createParagraphBlockConfig
|
|
11
|
+
>;
|
|
12
|
+
|
|
13
|
+
export const createParagraphBlockConfig = createBlockConfig(
|
|
14
|
+
() =>
|
|
15
|
+
({
|
|
16
|
+
type: "paragraph" as const,
|
|
17
|
+
propSchema: defaultProps,
|
|
18
|
+
content: "inline" as const,
|
|
19
|
+
}) as const,
|
|
20
|
+
);
|
|
21
|
+
|
|
22
|
+
export const createParagraphBlockSpec = createBlockSpec(
|
|
23
|
+
createParagraphBlockConfig,
|
|
24
|
+
{
|
|
25
|
+
meta: {
|
|
26
|
+
isolating: false,
|
|
27
|
+
},
|
|
28
|
+
parse: (e) => {
|
|
29
|
+
if (e.tagName !== "P") {
|
|
30
|
+
return undefined;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
// Edge case for things like images directly inside paragraph.
|
|
34
|
+
if (!e.textContent?.trim()) {
|
|
35
|
+
return undefined;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
return parseDefaultProps(e);
|
|
39
|
+
},
|
|
40
|
+
render: () => {
|
|
41
|
+
const dom = document.createElement("p");
|
|
42
|
+
return {
|
|
43
|
+
dom,
|
|
44
|
+
contentDOM: dom,
|
|
45
|
+
};
|
|
46
|
+
},
|
|
47
|
+
toExternalHTML: (block) => {
|
|
48
|
+
const dom = document.createElement("p");
|
|
49
|
+
addDefaultPropsExternalHTML(block.props, dom);
|
|
50
|
+
return {
|
|
51
|
+
dom,
|
|
52
|
+
contentDOM: dom,
|
|
53
|
+
};
|
|
54
|
+
},
|
|
55
|
+
runsBefore: ["default"],
|
|
56
|
+
},
|
|
57
|
+
[
|
|
58
|
+
createBlockNoteExtension({
|
|
59
|
+
key: "paragraph-shortcuts",
|
|
60
|
+
keyboardShortcuts: {
|
|
61
|
+
"Mod-Alt-0": ({ editor }) => {
|
|
62
|
+
const cursorPosition = editor.getTextCursorPosition();
|
|
63
|
+
|
|
64
|
+
if (
|
|
65
|
+
editor.schema.blockSchema[cursorPosition.block.type].content !==
|
|
66
|
+
"inline"
|
|
67
|
+
) {
|
|
68
|
+
return false;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
editor.updateBlock(cursorPosition.block, {
|
|
72
|
+
type: "paragraph",
|
|
73
|
+
props: {},
|
|
74
|
+
});
|
|
75
|
+
return true;
|
|
76
|
+
},
|
|
77
|
+
},
|
|
78
|
+
}),
|
|
79
|
+
],
|
|
80
|
+
);
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import { createBlockNoteExtension } from "../../editor/BlockNoteExtension.js";
|
|
2
|
+
import { createBlockConfig, createBlockSpec } from "../../schema/index.js";
|
|
3
|
+
import {
|
|
4
|
+
addDefaultPropsExternalHTML,
|
|
5
|
+
defaultProps,
|
|
6
|
+
parseDefaultProps,
|
|
7
|
+
} from "../defaultProps.js";
|
|
8
|
+
|
|
9
|
+
export type QuoteBlockConfig = ReturnType<typeof createQuoteBlockConfig>;
|
|
10
|
+
|
|
11
|
+
export const createQuoteBlockConfig = createBlockConfig(
|
|
12
|
+
() =>
|
|
13
|
+
({
|
|
14
|
+
type: "quote" as const,
|
|
15
|
+
propSchema: {
|
|
16
|
+
backgroundColor: defaultProps.backgroundColor,
|
|
17
|
+
textColor: defaultProps.textColor,
|
|
18
|
+
},
|
|
19
|
+
content: "inline" as const,
|
|
20
|
+
}) as const,
|
|
21
|
+
);
|
|
22
|
+
|
|
23
|
+
export const createQuoteBlockSpec = createBlockSpec(
|
|
24
|
+
createQuoteBlockConfig,
|
|
25
|
+
{
|
|
26
|
+
meta: {
|
|
27
|
+
isolating: false,
|
|
28
|
+
},
|
|
29
|
+
parse(element) {
|
|
30
|
+
if (element.tagName === "BLOCKQUOTE") {
|
|
31
|
+
const { backgroundColor, textColor } = parseDefaultProps(element);
|
|
32
|
+
|
|
33
|
+
return { backgroundColor, textColor };
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
return undefined;
|
|
37
|
+
},
|
|
38
|
+
render() {
|
|
39
|
+
const quote = document.createElement("blockquote");
|
|
40
|
+
|
|
41
|
+
return {
|
|
42
|
+
dom: quote,
|
|
43
|
+
contentDOM: quote,
|
|
44
|
+
};
|
|
45
|
+
},
|
|
46
|
+
toExternalHTML(block) {
|
|
47
|
+
const quote = document.createElement("blockquote");
|
|
48
|
+
addDefaultPropsExternalHTML(block.props, quote);
|
|
49
|
+
|
|
50
|
+
return {
|
|
51
|
+
dom: quote,
|
|
52
|
+
contentDOM: quote,
|
|
53
|
+
};
|
|
54
|
+
},
|
|
55
|
+
},
|
|
56
|
+
[
|
|
57
|
+
createBlockNoteExtension({
|
|
58
|
+
key: "quote-block-shortcuts",
|
|
59
|
+
keyboardShortcuts: {
|
|
60
|
+
"Mod-Alt-q": ({ editor }) => {
|
|
61
|
+
const cursorPosition = editor.getTextCursorPosition();
|
|
62
|
+
|
|
63
|
+
if (
|
|
64
|
+
editor.schema.blockSchema[cursorPosition.block.type].content !==
|
|
65
|
+
"inline"
|
|
66
|
+
) {
|
|
67
|
+
return false;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
editor.updateBlock(cursorPosition.block, {
|
|
71
|
+
type: "quote",
|
|
72
|
+
props: {},
|
|
73
|
+
});
|
|
74
|
+
return true;
|
|
75
|
+
},
|
|
76
|
+
},
|
|
77
|
+
inputRules: [
|
|
78
|
+
{
|
|
79
|
+
find: new RegExp(`^>\\s$`),
|
|
80
|
+
replace() {
|
|
81
|
+
return {
|
|
82
|
+
type: "quote",
|
|
83
|
+
props: {},
|
|
84
|
+
};
|
|
85
|
+
},
|
|
86
|
+
},
|
|
87
|
+
],
|
|
88
|
+
}),
|
|
89
|
+
],
|
|
90
|
+
);
|