Javascript 由于有许多装饰器,所以随着内容的增加,Draft js Editor的速度会变慢
因此,我插入的内容越多(大约替换了20个decorator之后),我的草稿js编辑器就变得非常慢(粗糙)。我猜这种行为是由于decorator使用regex检查整个编辑器内容,并在每次状态更改时用emoji组件替换匹配项。我还为regex查找的每个匹配项创建实体,我通过使用编辑器状态作为道具装饰组件来实现这一点。有没有办法让它更快? 这是我的装饰师:Javascript 由于有许多装饰器,所以随着内容的增加,Draft js Editor的速度会变慢,javascript,reactjs,draftjs,Javascript,Reactjs,Draftjs,因此,我插入的内容越多(大约替换了20个decorator之后),我的草稿js编辑器就变得非常慢(粗糙)。我猜这种行为是由于decorator使用regex检查整个编辑器内容,并在每次状态更改时用emoji组件替换匹配项。我还为regex查找的每个匹配项创建实体,我通过使用编辑器状态作为道具装饰组件来实现这一点。有没有办法让它更快? 这是我的装饰师: { strategy: emojiStrategy, component: deco
{
strategy: emojiStrategy,
component: decorateComponentWithProps(RenderEmoji, {
getEditorState: this.getEditorState,
setEditorState: this.onChange
})
}
这是我的表情策略:
function emojiRegexF(regex, contentBlock, callback, contentState) {
const text = contentBlock.getText();
let matchArr, start;
while ((matchArr = regex.exec(text)) !== null) {
start = matchArr.index;
callback(start, start + matchArr[0].length);
}
}
function emojiStrategy(contentBlock, callback, contentState) {
emojiRegexF(EMOJI_REGEX, contentBlock, callback, contentState);
}
以下是我的RenderoJi组件:
const RenderEmoji = props => {
const contentBlock = props.children[0].props.block;
const emojiKey = contentBlock.getEntityAt(props.children[0].props.start);
const emojiShortName = props.decoratedText;
if (!emojiKey) {
setEntity(props, emojiShortName);
}
return (
<Emoji emoji={emojiShortName} set="emojione" size={24}>
{props.children}
</Emoji>
);
};
我能优化一下吗?谢谢我不确定这是否会导致任何真正的性能问题,但有两件事看起来很有趣:
- 通过正则表达式匹配表情装饰符,即使您正在为它们创建实体
- 在呈现装饰器期间更改编辑器状态(通过
)。渲染函数setEntity
setEntity
逻辑将emojis的实体作为onChange
的一部分插入const emojiStrategy=(contentBlock、回调、contentState)=>{
contentBlock.findEntityRanges(字符=>{
const entityKey=character.getEntity();
返回(
entityKey!==null&&
contentState.getEntity(entityKey).getType()==='emoji'
);
},回调);
};
这样,装饰器组件就不需要在渲染期间更新编辑器状态。您也可能不再需要使用decorecomponentwithprops
现在回到性能上来——对于您来说,确定如何提高性能的最佳方法是。您将能够准确地知道在击键期间渲染所需的时间,然后跟踪问题。谢谢,这似乎是一个可能的解决方案。还有一个问题,有没有办法使实体不可编辑(而不是不可变的)?就像我有这些装饰符,它们的短名称是props.children中的文本,所以当我在编辑器中使用左箭头返回时,我仍然可以更改表情文字的值,这会破坏实体并使装饰符发生更改。我想要的是,装饰师创建的表情图像被视为单个字符,用户不能像不可变实体那样编辑它,但也不能编辑它。希望这能让你sense@AliZeaiter这可能需要一个单独的问题而不是评论。我想我应该尝试用一个空格来替换表情符号,这样实体总是一个字符(就像原子块一样)。如果您使实体
不可变
,我认为用户不可能更改字符。
function setEntity(props, emojiShortName) {
const editorState = props.getEditorState();
const contentstate = editorState.getCurrentContent();
const contentStateWithEntity = contentstate.createEntity(
"emoji",
"IMMUTABLE",
{
emojiUnicode: emojiShortName
}
);
const entityKey = contentStateWithEntity.getLastCreatedEntityKey();
const oldSelectionState = editorState.getSelection();
const selectionState = oldSelectionState.merge({
focusOffset: props.children[0].props.start + props.decoratedText.length,
anchorOffset: props.children[0].props.start
});
const newContentState = Modifier.applyEntity(
contentstate,
selectionState,
entityKey
);
const withBlank = Modifier.replaceText(
newContentState,
selectionState,
emojiShortName + " ",
null,
entityKey
);
const newEditorState = EditorState.push(
editorState,
withBlank,
"apply-entity"
);
props.setEditorState(newEditorState);
}