使用词法文本编辑器框架,在 React 中使用默认文本字符串初始化编辑器的最简单方法是什么?
例如,我可以创建一个实例,手动保存 JSON 状态,然后将该 JSON blob 复制到我的代码中,以设置为initialEditorState,PlainTextPlugin但这似乎我必须缺少一些东西。
谢谢
zur*_*fyx 13
你的直觉是正确的。避免直接接触 EditorState,即使它被序列化为 JSON。操纵内部结构(包括节点私有属性)可能会导致未来版本中出现意外的行为/错误。
这initialEditorState采取多种形状:
export type InitialEditorStateType = null | string | EditorState | (() => void);
null-> 空 EditorState (只是一个 RootNode)string-> JSON 字符串化的 EditorState。它在幕后调用JSON.parse(editor.setEditorState)EditorState-> 一个编辑器状态。它在幕后调用 - editor.setEditorState()(undo-redo/History 插件使用这个)
(() => void)->editor.update函数您感兴趣的是(() => void)-> 编辑器更新。
您可以运行editor.update如下所示:
<LexicalPlainTextPlugin initialEditorState={() => {
const paragraph = $createParagraphNode();
const text = $createTextNode('foo');
paragraph.append(text);
$getRoot().append(paragraph);
$getRoot().selectEnd();
}} />
Run Code Online (Sandbox Code Playgroud)
无需缓存(useCallback)initialEditorState,因为它只处理一次
旁注:我们计划搬到initialEditorState(目前居住在LexicalPlainTextPlugin和LexicalRichTextPlugin),LexicalComposer但它会以同样的方式工作。
我们建议也避免手动制作的解决方案:
// PrepopulatePlugin.js
useLayoutEffect(() => {
editor.update(() => {
// Prepopulate
});
}, [editor]);
Run Code Online (Sandbox Code Playgroud)
我们构建了 LexicalContentEditable 来与 SSR 很好地配合并进行contenteditable适当的处理。如果您要构建自己的自定义解决方案,则必须重复此过程。
Jer*_*ier 10
您可以通过设置editorState为字符串化 JSON 状态或强制填充编辑器的函数来设置默认文本。
方法 #1 - 初始化editorState为字符串化 JSON 状态
editorState您可以通过设置为字符串化 JSON 状态来设置初始内容。
const EMPTY_CONTENT =
'{"root":{"children":[{"children":[],"direction":null,"format":"","indent":0,"type":"paragraph","version":1}],"direction":null,"format":"","indent":0,"type":"root","version":1}}';
const initialConfig = {
...
editorState: EMPTY_CONTENT,
...
}
const Editor = () => {
return (
<LexicalComposer initialConfig={initialConfig}>
...
</LexicalComposer>
);
}
Run Code Online (Sandbox Code Playgroud)
请注意,您可以通过以下方式检索 JSON 状态 onChangePlugin:
import { OnChangePlugin } from "@lexical/react/LexicalOnChangePlugin";
...
const onChange = (editorState) => {
editorState.read(() => {
const json = editorState.toJSON();
console.log(JSON.stringify(json));
})
}
...
return (
<LexicalComposer initialConfig={initialConfig}>
...
<OnChangePlugin onChange={onChange} />
</LexicalComposer>
Run Code Online (Sandbox Code Playgroud)
方法 #2 - 初始化editorState为强制填充编辑器的函数
或者,您可以将其设置editorState为这样的函数,该函数强制初始化编辑器(这就是下面示例中的完成方式):
function prepopulatedRichText() {
const root = $getRoot();
if (root.getFirstChild() === null) {
const paragraph = $createParagraphNode();
paragraph.append(
$createTextNode("The playground is a demo environment built with "),
$createTextNode("@lexical/react").toggleFormat("code"),
$createTextNode("."),
$createTextNode(" Try typing in "),
$createTextNode("some text").toggleFormat("bold"),
$createTextNode(" with "),
$createTextNode("different").toggleFormat("italic"),
$createTextNode(" formats.")
);
root.append(paragraph);
}
}
const initialConfig = {
...
editorState: prepopulatedRichText,
...
}
Run Code Online (Sandbox Code Playgroud)
以下是文档中的相关页面:
以下是默认使用初始文本的词法编辑器的示例:
小智 1
在词法代码库中找到的实现方法如下
\n//...\n<RichTextPlugin\n initialEditorState={ prepopulatedRichText}/>\n//...\n\nfunction prepopulatedRichText() {\n const root = $getRoot();\n if (root.getFirstChild() === null) {\n const heading = $createHeadingNode(\'h1\');\n heading.append($createTextNode(\'Welcome to the playground\'));\n root.append(heading);\n const quote = $createQuoteNode();\n quote.append(\n $createTextNode(\n `In case you were wondering what the black box at the bottom is \xe2\x80\x93 it\'s the debug view, showing the current state of editor. ` +\n `You can hide it by pressing on the settings control in the bottom-right of your screen and toggling the debug view setting.`,\n ),\n );\n root.append(quote);\n const paragraph = $createParagraphNode();\n paragraph.append(\n $createTextNode(\'The playground is a demo environment built with \'),\n $createTextNode(\'@lexical/react\').toggleFormat(\'code\'),\n $createTextNode(\'.\'),\n $createTextNode(\' Try typing in \'),\n $createTextNode(\'some text\').toggleFormat(\'bold\'),\n $createTextNode(\' with \'),\n $createTextNode(\'different\').toggleFormat(\'italic\'),\n $createTextNode(\' formats.\'),\n );\n root.append(paragraph);\n const paragraph2 = $createParagraphNode();\n paragraph2.append(\n $createTextNode(\n \'Make sure to check out the various plugins in the toolbar. You can also use #hashtags or @-mentions too!\',\n ),\n );\n root.append(paragraph2);\n const paragraph3 = $createParagraphNode();\n paragraph3.append(\n $createTextNode(`If you\'d like to find out more about Lexical, you can:`),\n );\n root.append(paragraph3);\n const list = $createListNode(\'bullet\');\n list.append(\n $createListItemNode().append(\n $createTextNode(`Visit the `),\n $createLinkNode(\'https://lexical.dev/\').append(\n $createTextNode(\'Lexical website\'),\n ),\n $createTextNode(` for documentation and more information.`),\n ),\n $createListItemNode().append(\n $createTextNode(`Check out the code on our `),\n $createLinkNode(\'https://github.com/facebook/lexical\').append(\n $createTextNode(\'GitHub repository\'),\n ),\n $createTextNode(`.`),\n ),\n $createListItemNode().append(\n $createTextNode(`Playground code can be found `),\n $createLinkNode(\n \'https://github.com/facebook/lexical/tree/main/packages/lexical-playground\',\n ).append($createTextNode(\'here\')),\n $createTextNode(`.`),\n ),\n $createListItemNode().append(\n $createTextNode(`Join our `),\n $createLinkNode(\'https://discord.com/invite/KmG4wQnnD9\').append(\n $createTextNode(\'Discord Server\'),\n ),\n $createTextNode(` and chat with the team.`),\n ),\n );\n root.append(list);\n const paragraph4 = $createParagraphNode();\n paragraph4.append(\n $createTextNode(\n `Lastly, we\'re constantly adding cool new features to this playground. So make sure you check back here when you next get a chance :).`,\n ),\n );\n root.append(paragraph4);\n }\n}\n\nRun Code Online (Sandbox Code Playgroud)\n但我更喜欢使用字符串化的editorState,然后通过实例拥有的parseEditorState函数将其解析为editorState。
\nParseEditorState是一个仅用于实例的函数,但我不能在init组件下使用useLexicalComposerContext,它将返回LexicalComposer(会导致意外错误),所以我需要编写一个额外的插件来实现它。像这样的东西:
\nimport { useSelector } from "react-redux";\nimport { useLexicalComposerContext } from "@lexical/react/LexicalComposerContext";\nimport { useEffect } from "react";\n\nexport default function EditorStatePlugin() {\n const activeNote = useSelector((state) => state.note.activeNote);\n const [editor] = useLexicalComposerContext();\n const state = editor.parseEditorState(\n activeNote?.content ||\n \'{"_nodeMap":[["root",{"__children":["1"],"__dir":null,"__format":0,"__indent":0,"__key":"root","__parent":null,"__type":"root"}],["1",{"__type":"paragraph","__parent":"root","__key":"1","__children":[],"__format":0,"__indent":0,"__dir":null}]],"_selection":{"anchor":{"key":"1","offset":0,"type":"element"},"focus":{"key":"1","offset":0,"type":"element"},"type":"range"}}\'\n );\n useEffect(() => {\n editor.setEditorState(state);\n }, [activeNote]);\n\n return null;\n}\nRun Code Online (Sandbox Code Playgroud)\n感觉写法不太好,请问有更好的写法吗?
\n| 归档时间: |
|
| 查看次数: |
12607 次 |
| 最近记录: |