我在渲染组件时会收到以下警告:
警告:组件是
contentEditable
,包含children
由React管理。现在您有责任保证没有 这些节点的中间是出乎意料地修改或重复的。这是 可能不是故意的。
这是我的组成部分:
import React, { Component } from "react";
export default class Editable extends Component {
render() {
return (
<div contentEditable={true} onBlur={this.props.handleBlur}>
{this.props.children}
</div>
);
}
}
https://github.com/lovasoa/react-contenteditable
的此组件不会生成警告。
import React from 'react';
let stripNbsp = str => str.replace(/ |u202F|u00A0/g, ' ');
export default class ContentEditable extends React.Component {
constructor() {
super();
this.emitChange = this.emitChange.bind(this);
}
render() {
var { tagName, html, ...props } = this.props;
return React.createElement(
tagName || 'div',
{
...props,
ref: (e) => this.htmlEl = e,
onInput: this.emitChange,
onBlur: this.props.onBlur || this.emitChange,
contentEditable: !this.props.disabled,
dangerouslySetInnerHTML: {__html: html}
},
this.props.children);
}
shouldComponentUpdate(nextProps) {
let { props, htmlEl } = this;
// We need not rerender if the change of props simply reflects the user's edits.
// Rerendering in this case would make the cursor/caret jump
// Rerender if there is no element yet... (somehow?)
if (!htmlEl) {
return true;
}
// ...or if html really changed... (programmatically, not by user edit)
if (
stripNbsp(nextProps.html) !== stripNbsp(htmlEl.innerHTML) &&
nextProps.html !== props.html
) {
return true;
}
let optional = ['style', 'className', 'disabled', 'tagName'];
// Handle additional properties
return optional.some(name => props[name] !== nextProps[name]);
}
componentDidUpdate() {
if ( this.htmlEl && this.props.html !== this.htmlEl.innerHTML ) {
// Perhaps React (whose VDOM gets outdated because we often prevent
// rerendering) did not update the DOM. So we update it manually now.
this.htmlEl.innerHTML = this.props.html;
}
}
emitChange(evt) {
if (!this.htmlEl) return;
var html = this.htmlEl.innerHTML;
if (this.props.onChange && html !== this.lastHtml) {
// Clone event with Object.assign to avoid
// "Cannot assign to read only property 'target' of object"
var evt = Object.assign({}, evt, {
target: {
value: html
}
});
this.props.onChange(evt);
}
this.lastHtml = html;
}
}
问题:
- 我的代码反应要警告我有什么潜在的问题?我从阅读
https://reactjs.org/docs/dom-elements.html
的文档中不太了解 - 为什么
https://github.com/lovasoa/react-contenteditable
的组件不生成相同的警告?
您所说的组件正在生成组件,请调用React.createElement
如下因此避免了警告:
function ContentEditable(props) {
return React.createElement('div', {contentEditable: true});
}
虽然您正在使用JSX。
function ContentEditable(props) {
return (<div contentEditable={true}></div>);
}
您可以在这里阅读更多有关为什么反应的信息警告你。如果您想压制警告,也可以使用 suppressContentEditableWarning
属性。
function ContentEditable(props) {
return (<div contentEditable={true} suppressContentEditableWarning={true}></div>);
}
设置contenteditable
时,请在浏览器中修改内容。
如果您不在后面进行反应管理而更改DOM,则反应会警告您,因为这可能会引起问题,例如更新这些元素。您正在传递直接来自React的{this.props.children}
,使用contenteditable
将使您的内容由浏览器中的用户修改,因此可能与React不再具有控制权可能不一样。
您可以使用suppressContentEditableWarning={true}
避免该警告。您要么可以使用React.createElement
并通过参数{contentEditable: true}
避免警告(如https://github.com/lovasoa/reaeact-contentedistication(
我不使用外部组件。我也有相同的问题,此外,如果我将div标记为内容可编辑的错误,我曾经获得无法使用dandernlyseinnerhtml的错误。我的方法与您的方法相似。因此,我没有将其标记为内容编辑。只是危险囊肿。但是在componentDidupdate中,我使用ref将DIV的套餐用作" contineDectibal = true"。我使用相同的Div抓住DIV内容进行保存。这停止了所有警告和错误。
componentDidUpdate(){
this.htmlEl.setAttribute("contenteditable", true);
}
另外,如果您的dangesslysetinnerhtml含量包含反应组件,则可以将它们保湿以使其功能正常。但是显然您需要知道Div内部的哪个组件进行补充。