我正在尝试使用reactjs 创建一个带有tiptap 的文本编辑器。我想在编辑器的每个“块”(paragraph块、blockquote块、codeblock块...)旁边创建一个按钮,允许用户在所选块之前添加一个新的空块。它看起来像这样(概念编辑器):
所以我尝试执行此操作的方法是将光标的位置设置在当前节点的末尾:
src/components/blocks/Paragraph.js
const Paragraph = (props) => {
// ...
return {
// ...
<button onMouseDown={() => {
// ...
// props.getPos() gives the position at the beginning of the block
// props.node.nodeSize gives the "length" of the node
const endPos = props.getPos() + props.node.nodeSize;
props.editor.commands.focus(endPos);
// ...
}}>
Add block below
</button>
}
}
Run Code Online (Sandbox Code Playgroud)
所以在这一点上,它有效。node但是,当我尝试在这个位置插入新的时......
// It will insert a paragraph node containing text "New block …Run Code Online (Sandbox Code Playgroud) 我正在考虑使用Slate或ProseMirror构建一个编辑器,并在使用内联元素时在插入符号位置和选择区域周围看到 Chrome 的一些奇怪行为。问题 1 显示在下面的第一张图片中。当文本光标位置在“f”后面时,插入符号显示在图像的顶部。问题 2 在第二张图片中 - 选择文本会显示一个与内联元素一样高的突出显示区域。有什么方法可以控制这种行为,而是在文本位置显示插入符号,并且只突出显示文本周围的空间(即使内嵌图像使行高变大)

示例图像是使用此处的 ProseMirror 演示生成的:https ://prosemirror.net/examples/basic/
JSBin 的最小示例(感谢@Kaiido):
<div contenteditable>Test text<img src="https://upload.wikimedia.org/wikipedia/en/9/9b/Yoda_Empire_Strikes_Back.png">Testing</div>
Run Code Online (Sandbox Code Playgroud)
不确定这在其他操作系统上的表现如何,但我使用的是 macOS Catalina。
我在一个接收字符串作为输入的函数中:
\n(text) => {\n\n}\nRun Code Online (Sandbox Code Playgroud)\n我可以通过 Vue props ( ) 访问编辑器props.editor。我想用此文本替换当前节点的内容。我似乎不知道如何做到这一点。我正在使用tiptap2,它是 ProseMirror 的包装器,可以访问 ProseMirror 的所有 api。
除非有必要,否则我宁愿不尝试替换整个节点,我也尝试过,在 \xe2\x80\x93 下面执行此操作,但也无法使其工作:
\n(text) => {\n props.editor\n .chain()\n .focus()\n .command(({ tr }) => {\n const node = props.editor.state.schema.nodes.paragraph.create(\n { content: text}\n );\n tr.replaceSelectionWith(node);\n\n return true;\n })\n .run();\n}\nRun Code Online (Sandbox Code Playgroud)\n非常感谢
\n我需要为我的 React 应用程序构建一个富文本编辑器。在使用 Draft.js 一个月后,我发现它的可配置性不足以满足我的需求。我在Slate和ProseMirror之间做出决定。
它们的优缺点是什么?
目前在 ProseMirror 中有点迷失,并试图了解替换当前选择的文本的正确方法。我希望能够在小写/大写之间切换。
state.selection.content();将返回选择下的相关节点的切片以及所选的内容,但不返回每个节点内需要替换的范围。
我假设我需要创建一个新的文本节点来替换每个选定节点内的范围,例如:
const updatedText = node.textContent.toUpperCase();
const textNode = state.schema.text(updatedText);
transaction = transaction.replaceWith(startPos, startPos + node.nodeSize, textNode);
Run Code Online (Sandbox Code Playgroud)
如何获取每个节点内要替换的范围?
不幸的是,我找不到合适的例子。
该代码可以工作,但绝对没有效果(节点未创建)
const PageNode = Node.create({
name: 'PageNode',
// content: 'block+',
content: 'inline*',
marks: '_',
inline: true,
group: "inline",
draggable: true,
code: true,
isolating: true,
defining: true,
// draggable: true
defaultOptions: {
HTMLAttributes: {
class: 'page pagebreak',
},
},
Run Code Online (Sandbox Code Playgroud)
这段代码会抛出一个错误
const PageNode = Node.create({
name: 'PageNode',
// content: 'block+',
content: 'block+',
marks: '_',
inline: false,
group: "block",
draggable: true,
code: true,
isolating: true,
defining: true,
// draggable: true
defaultOptions: {
HTMLAttributes: {
class: 'page pagebreak',
},
},
addAttributes() {
// Return …Run Code Online (Sandbox Code Playgroud) 我正在尝试将 ProseMirror 的 JSON 输出转换回 HTML(将它从一个数据库保存到另一个数据库)。我是 ProseMirror 的新手,我不确定我是否完全理解模型、状态和模式之间的关系。
从我阅读的内容来看https://github.com/ProseMirror/prosemirror/issues/455和https://discuss.prosemirror.net/t/example-of-converting-between-formats-for-the- purpose-储蓄/424 ,
我应该首先基于基本模式创建一个新状态,然后使用 DOMSerializer 并将输出附加到一个临时元素(然后获取 innerHtml)。那个听起来是对的吗?任何帮助将不胜感激。
我想建立一个使用所见即所得的网站,例如 ProseMirror。他们的文档有点清楚,因为他们首先专注于开发的其他部分,因此构建所有内容并不是一个简单的过程。但是,它们确实提供了一个可以克隆和运行的项目。
但是,我不确定如何实际运行此示例。
我在我的活动 MAMP 目录中创建了一个新文件夹,并完成npm install了获取 package.json 中的所有项目。然后我已经运行,npm run build以便项目现在内置到distpackage.json 中默认指定的文件夹中。
但是,我如何真正让它在浏览器中运行?如果我转到浏览器,它只是显示我的文件和文档列表,而不是实际的应用程序。
我也试过运行,npm start但在 package.json 中没有任何链接的命令。我确实看到这是使用 rollup.js。我以前没有用过,也许有一些命令?
我有一个协作聊天应用程序,它使用Tiptap作为其消息传递区域。我发现它很有用,因为它已经可以支持多种格式并且可以增加一些灵活性。然而,在寻找侦听“enter”键的事件侦听器时,我发现自己陷入了困境。当用户按下回车键时,我想提交他们的聊天并清除编辑器。
我找到了这个onUpdate事件侦听器,但我找不到它检测按下哪个键的确切位置。
示例代码如下:
mounted() {
let editor = new Editor({
extensions: [StarterKit],
content: this.value
});
editor.on("update", e => {
console.log(e);
this.$emit("input", this.editor.getHTML());
});
this.editor = editor;
}
Run Code Online (Sandbox Code Playgroud)
顺便说一句,我正在使用 Vue2。
谢谢
运行命令({ href: url })后,我想取消选择当前选择并将插入符位置设置为所选节点的末尾。注意:我正在使用 TipTap
setLinkUrl(command, url) {
command({ href: url })
this.hideLinkMenu()
// Set cursor position after highlighted link
var tag = document.getElementById("editor")
var setpos = document.createRange()
var set = window.getSelection()
const state = this.editor.state
let sel = state.selection
// TODO: Check if sel range > 0
let resolvedPos = state.doc.resolve(sel.from)
let node = resolvedPos.node(resolvedPos.depth)
// This is where I want to set the caret position to the end of the currently selected node
// Currently, I'm using hardcoded …Run Code Online (Sandbox Code Playgroud) 我开始使用 prosemirror,但我正在努力寻找它的扩展。即使是标签、提及或表情符号等基本扩展也很难找到。我是不是错过了这个编辑器的某些东西?我知道它已经相当成熟(试图放弃草稿以支持它),但我可能会错过这里的一些东西。
prose-mirror ×11
tiptap ×5
javascript ×3
vue.js ×2
css ×1
html ×1
npm ×1
reactjs ×1
richtextbox ×1
slate.js ×1
slatejs ×1
text-editor ×1
vuejs3 ×1
wysiwyg ×1