tiptap: fix paste without title extension

This commit is contained in:
fantasticit 2022-06-13 17:47:04 +08:00
parent e50b81cb4f
commit c6fc458ae3
3 changed files with 23 additions and 5 deletions

View File

@ -15,6 +15,8 @@ import {
normalizeMarkdown, normalizeMarkdown,
} from 'tiptap/prose-utils'; } from 'tiptap/prose-utils';
import { TitleExtensionName } from './title';
interface IPasteOptions { interface IPasteOptions {
/** /**
* *
@ -26,7 +28,7 @@ interface IPasteOptions {
* markdown prosemirror * markdown prosemirror
* FIXME: prosemirror * FIXME: prosemirror
*/ */
markdownToProsemirror: (arg: { schema: Schema; content: string; hasTitle: boolean }) => unknown; markdownToProsemirror: (arg: { schema: Schema; content: string; needTitle: boolean }) => unknown;
/** /**
* prosemirror markdown * prosemirror markdown
@ -100,6 +102,13 @@ export const Paste = Extension.create<IPasteOptions>({
const { markdownToProsemirror } = extensionThis.options; const { markdownToProsemirror } = extensionThis.options;
console.log('p', {
text,
html,
node,
markdownText,
});
// 直接复制节点 // 直接复制节点
if (node) { if (node) {
const json = safeJSONParse(node); const json = safeJSONParse(node);
@ -159,13 +168,18 @@ export const Paste = Extension.create<IPasteOptions>({
if (markdownText || isMarkdown(text) || html.length === 0 || pasteCodeLanguage === 'markdown') { if (markdownText || isMarkdown(text) || html.length === 0 || pasteCodeLanguage === 'markdown') {
event.preventDefault(); event.preventDefault();
const firstNode = view.props.state.doc.content.firstChild; const firstNode = view.props.state.doc.content.firstChild;
const hasTitleExtension = !!editor.extensionManager.extensions.find(
(extension) => extension.name === TitleExtensionName
);
const hasTitle = isTitleNode(firstNode) && firstNode.content.size > 0; const hasTitle = isTitleNode(firstNode) && firstNode.content.size > 0;
const schema = view.props.state.schema; const schema = view.props.state.schema;
const doc = markdownToProsemirror({ const doc = markdownToProsemirror({
schema, schema,
content: normalizeMarkdown(markdownText || text), content: normalizeMarkdown(markdownText || text),
hasTitle, needTitle: hasTitleExtension && !hasTitle,
}); });
console.log('p', markdownText, text);
let tr = view.state.tr; let tr = view.state.tr;
const selection = tr.selection; const selection = tr.selection;
view.state.doc.nodesBetween(selection.from, selection.to, (node, position) => { view.state.doc.nodesBetween(selection.from, selection.to, (node, position) => {

View File

@ -18,9 +18,13 @@ declare module '@tiptap/core' {
} }
} }
export const TitleExtensionName = 'title';
export const Title = Node.create<TitleOptions>({ export const Title = Node.create<TitleOptions>({
name: 'title', name: TitleExtensionName,
content: 'inline*', content: 'inline*',
group: 'block',
selectable: true,
addOptions() { addOptions() {
return { return {

View File

@ -25,7 +25,7 @@ const extractImage = (html) => {
}; };
// 将 markdown 字符串转换为 ProseMirror JSONDocument // 将 markdown 字符串转换为 ProseMirror JSONDocument
export const markdownToProsemirror = ({ schema, content, hasTitle }) => { export const markdownToProsemirror = ({ schema, content, needTitle }) => {
const html = markdownToHTML(content); const html = markdownToHTML(content);
if (!html) return null; if (!html) return null;
@ -34,7 +34,7 @@ export const markdownToProsemirror = ({ schema, content, hasTitle }) => {
const { body } = parser.parseFromString(extractImage(html), 'text/html'); const { body } = parser.parseFromString(extractImage(html), 'text/html');
body.append(document.createComment(content)); body.append(document.createComment(content));
const node = htmlToPromsemirror(body, !hasTitle); const node = htmlToPromsemirror(body, needTitle);
return node; return node;
}; };