警告:findDOMNode 在 StrictMode 中已弃用。 findDOMNode 被传递给 StrictMode 中的 Transition 实例
Warning: findDOMNode is deprecated in StrictMode. findDOMNode was passed an instance of Transition which is inside StrictMode
我正在尝试将函数用作组件内的道具,而该组件是另一个组件的子组件。但是这个功能不起作用。?我能知道为什么吗。这是我在控制台收到的警告。
Warning: findDOMNode is deprecated in StrictMode. findDOMNode was passed an instance of Transition which is inside StrictMode. Instead, add a ref directly to the element you want to reference
这是我的代码
class Todo extends Component {
state = {
show: false,
editTodo: {
id: "",
title: "",
isCompleted: false
}
}
handleClose = () => {
this.setState({ show: false })
}
handleShow = () => {
this.setState({ show: true })
}
getStyle () {
return {
background: '#f4f4f4',
padding: '10px',
borderBottom: '1px #ccc dotted',
textDecoration: this.props.todo.isCompleted ? 'line-through'
: 'none'
}
}
//this method checks for changes in the edit field
handleChange = (event) => {
this.setState({ title: event.target.value })
console.log(this.state.editTodo.title);
}
render () {
//destructuring
const { id, title } = this.props.todo;
return (
<div style={this.getStyle()}>
<p>
<input type='checkbox' style={{ margin: "0px 20px" }} onChange={this.props.markComplete.bind(this, id)} /> {''}
{title}
<Button style={{ float: "right", margin: "0px 10px" }} variant="warning" size={"sm"} onClick={this.handleShow}>Edit</Button>{' '}
<Button style={{ float: "right" }} variant="danger" size={"sm"} onClick={this.props.DelItem.bind(this, id)}>Delete</Button>
</p>
<Modal show={this.state.show} onHide={this.handleClose}>
<Modal.Header closeButton>
<Modal.Title>Edit your Task!</Modal.Title>
</Modal.Header>
<Modal.Body >
<FormGroup >
<Form.Control
type="text"
value={this.state.editTodo.title}
onChange={this.handleChange}
/>
</FormGroup>
</Modal.Body>
<Modal.Footer>
<Button variant="secondary" onClick={this.handleClose}>
Close
</Button>
<Button variant="primary" onClick={this.handleClose}>
Save Changes
</Button>
</Modal.Footer>
</Modal>
</div>
)
}
}
setState
调用似乎被写入了错误的位置。确保它在 editTodo
对象上:
handleChange = (event) => {
this.setState(state => ({
editTodo: {
...state.editTodo,
title: event.target.value,
},
}));
}
在 index.js 中将 <React.StrictMode><App /><React.StrictMode>
更改为 <App />
,您将不会看到此警告。请注意,严格模式可以帮助您
- 识别具有不安全生命周期的组件
- 有关遗留字符串引用 API 用法的警告
- 有关已弃用的 findDOMNode 用法的警告
- 检测意外的副作用
- 检测遗留上下文API
@Ross Allen 的回复与基本问题(警告)无关,它解决了代码中的语法问题。
@Ali Rehman 的回应与警告更相关,但也没有正确解决问题,它只是隐藏问题,这样警告就不会再出现了。如果我们不关心弃用,为什么不呢!!
是的,问题来自 React.StrictMode:
<React.StrictMode>
<App />
</React.StrictMode>
StrictMode 是一种用于突出显示应用程序中潜在问题的工具。它为其后代激活额外的检查和警告,例如:
- 识别具有不安全生命周期的组件
- 有关遗留字符串引用 API 用法的警告
- 有关已弃用查找的警告DOM节点使用
- 检测意外的副作用
- 检测遗留上下文API
由于问题中没有完全给出错误回溯,我猜这个问题与 Warning about deprecated findDOMNode usage 有关,因为引用渲染方法中的元素:
<Modal show={this.state.show} onHide={this.handleClose}>
<Modal.Header closeButton>
<Modal.Title>Edit your Task!</Modal.Title>
</Modal.Header>
<Modal.Body >
<FormGroup >
<Form.Control
type="text"
value={this.state.editTodo.title}
onChange={this.handleChange}
/>
</FormGroup>
</Modal.Body>
<Modal.Footer>
<Button variant="secondary" onClick={this.handleClose}>
Close
</Button>
<Button variant="primary" onClick={this.handleClose}>
Save Changes
</Button>
</Modal.Footer>
</Modal>
当组件被渲染时,modal也被渲染了,我们尝试改变组件的状态,组件(以及modal)将重新渲染,而在这个阶段modal不能可以访问各州。
解决警告的方法是使用React refs。 Refs 有助于访问 DOM 节点或在 render 方法中创建的 React 元素。
如果您使用来自 react-bootstrap
的模式或轮播,解决方法是禁用 动画 。关闭它们会使警告消失。
对于模态:
<Modal animation={false}>
<Modal.Header closeButton>
<Modal.Title>Title</Modal.Title>
</Modal.Header>
<Modal.Body>
Content
</Modal.Body>
</Modal>
对于轮播:
<Carousel slide={false} fade={false}>
<Carousel.Item>
Scene 1
</Carousel.Item>
<Carousel.Item>
Scene 2
</Carousel.Item>
</Carousel>
我知道一旦它没有回答 OP 问题,它更适合作为评论,但我没有足够的声誉来这样做,也许它对某人有帮助。
此类情况的最简单解决方案是用 DOM 元素包装您的组件,您实际上可以将 ref 附加到它。例如:
import React, { createRef, Component } from "react";
import ChildComponent from "./child-component";
class MyComponent extends Component {
componentDidMount() {
const node = this.wrapper.current;
/* Uses DOM node */
}
wrapper = createRef();
render () {
return (
<div ref={this.wrapper}>
<ChildComponent>{this.props.children}</ChildComponent>
</div>
);
}
}
export default MyComponent;`
要解决此问题,只需从访问 dom root id 的 index.js 中删除 React.StrictMode,即可解决问题。
而不是这个:
ReactDOM.render(
<React.StrictMode>
<App />
</React.StrictMode>,
document.getElementById('root')
);
使用这一行:
ReactDOM.render(<App />,document.getElementById('root'));
我不确定它在使用 material-ui 库时是否有帮助,但在很多情况下这会有所帮助:
const nodeRef = React.useRef(null);
return <div>
<CSSTransition ... nodeRef={nodeRef}>
<div ref={nodeRef}> ... </div>
</CSSTransition>
</div>
类似问题:
下面解决了问题:
在ReactDOM.render()
函数中,更改
来自
<React.StrictMode>
<SnackbarProvider>
<App/>
</SnackbarProvider>
</React.StrictMode>
至
<SnackbarProvider>
<React.StrictMode>
<App/>
</React.StrictMode>
</SnackbarProvider>
注意:SnackbarProvider
和 React.StrictMode
标签是相反的。
我以前见过这个错误,当我同时使用 react-bootstrap 和 react-router-dom 时
彼此 。
我替换了
<Link to="/foo">sth</Link>
和
<LinkContainer to="/foo/bar">
<Button>Foo</Button>
</LinkContainer>
并且无需使用 Link 进行导航Link
这是 Material UI 库的问题,在新的 Material UI v5 正式发布之前temporary solution这里
我认为这个问题不是错误,而是弃用警告。库组件仍然有效,但使用了未来版本中将不再可用的功能。因此必须更新库以使用另一个函数来替换旧函数。
在 Semantic UI React 中,这是一个 known issue, most of their components are still using findDOMNode()
. This will be fixed in the Semantic UI React v3,其中所有这些组件都将更新为使用 React.forwardRef()
。
起初我以为我做错了什么,花了很多时间调查,才发现这是一个已知问题。
我正在尝试将函数用作组件内的道具,而该组件是另一个组件的子组件。但是这个功能不起作用。?我能知道为什么吗。这是我在控制台收到的警告。
Warning: findDOMNode is deprecated in StrictMode. findDOMNode was passed an instance of Transition which is inside StrictMode. Instead, add a ref directly to the element you want to reference
这是我的代码
class Todo extends Component {
state = {
show: false,
editTodo: {
id: "",
title: "",
isCompleted: false
}
}
handleClose = () => {
this.setState({ show: false })
}
handleShow = () => {
this.setState({ show: true })
}
getStyle () {
return {
background: '#f4f4f4',
padding: '10px',
borderBottom: '1px #ccc dotted',
textDecoration: this.props.todo.isCompleted ? 'line-through'
: 'none'
}
}
//this method checks for changes in the edit field
handleChange = (event) => {
this.setState({ title: event.target.value })
console.log(this.state.editTodo.title);
}
render () {
//destructuring
const { id, title } = this.props.todo;
return (
<div style={this.getStyle()}>
<p>
<input type='checkbox' style={{ margin: "0px 20px" }} onChange={this.props.markComplete.bind(this, id)} /> {''}
{title}
<Button style={{ float: "right", margin: "0px 10px" }} variant="warning" size={"sm"} onClick={this.handleShow}>Edit</Button>{' '}
<Button style={{ float: "right" }} variant="danger" size={"sm"} onClick={this.props.DelItem.bind(this, id)}>Delete</Button>
</p>
<Modal show={this.state.show} onHide={this.handleClose}>
<Modal.Header closeButton>
<Modal.Title>Edit your Task!</Modal.Title>
</Modal.Header>
<Modal.Body >
<FormGroup >
<Form.Control
type="text"
value={this.state.editTodo.title}
onChange={this.handleChange}
/>
</FormGroup>
</Modal.Body>
<Modal.Footer>
<Button variant="secondary" onClick={this.handleClose}>
Close
</Button>
<Button variant="primary" onClick={this.handleClose}>
Save Changes
</Button>
</Modal.Footer>
</Modal>
</div>
)
}
}
setState
调用似乎被写入了错误的位置。确保它在 editTodo
对象上:
handleChange = (event) => {
this.setState(state => ({
editTodo: {
...state.editTodo,
title: event.target.value,
},
}));
}
在 index.js 中将 <React.StrictMode><App /><React.StrictMode>
更改为 <App />
,您将不会看到此警告。请注意,严格模式可以帮助您
- 识别具有不安全生命周期的组件
- 有关遗留字符串引用 API 用法的警告
- 有关已弃用的 findDOMNode 用法的警告
- 检测意外的副作用
- 检测遗留上下文API
@Ross Allen 的回复与基本问题(警告)无关,它解决了代码中的语法问题。
@Ali Rehman 的回应与警告更相关,但也没有正确解决问题,它只是隐藏问题,这样警告就不会再出现了。如果我们不关心弃用,为什么不呢!!
是的,问题来自 React.StrictMode:
<React.StrictMode>
<App />
</React.StrictMode>
StrictMode 是一种用于突出显示应用程序中潜在问题的工具。它为其后代激活额外的检查和警告,例如:
- 识别具有不安全生命周期的组件
- 有关遗留字符串引用 API 用法的警告
- 有关已弃用查找的警告DOM节点使用
- 检测意外的副作用
- 检测遗留上下文API
由于问题中没有完全给出错误回溯,我猜这个问题与 Warning about deprecated findDOMNode usage 有关,因为引用渲染方法中的元素:
<Modal show={this.state.show} onHide={this.handleClose}>
<Modal.Header closeButton>
<Modal.Title>Edit your Task!</Modal.Title>
</Modal.Header>
<Modal.Body >
<FormGroup >
<Form.Control
type="text"
value={this.state.editTodo.title}
onChange={this.handleChange}
/>
</FormGroup>
</Modal.Body>
<Modal.Footer>
<Button variant="secondary" onClick={this.handleClose}>
Close
</Button>
<Button variant="primary" onClick={this.handleClose}>
Save Changes
</Button>
</Modal.Footer>
</Modal>
当组件被渲染时,modal也被渲染了,我们尝试改变组件的状态,组件(以及modal)将重新渲染,而在这个阶段modal不能可以访问各州。
解决警告的方法是使用React refs。 Refs 有助于访问 DOM 节点或在 render 方法中创建的 React 元素。
如果您使用来自 react-bootstrap
的模式或轮播,解决方法是禁用 动画 。关闭它们会使警告消失。
对于模态:
<Modal animation={false}>
<Modal.Header closeButton>
<Modal.Title>Title</Modal.Title>
</Modal.Header>
<Modal.Body>
Content
</Modal.Body>
</Modal>
对于轮播:
<Carousel slide={false} fade={false}>
<Carousel.Item>
Scene 1
</Carousel.Item>
<Carousel.Item>
Scene 2
</Carousel.Item>
</Carousel>
我知道一旦它没有回答 OP 问题,它更适合作为评论,但我没有足够的声誉来这样做,也许它对某人有帮助。
此类情况的最简单解决方案是用 DOM 元素包装您的组件,您实际上可以将 ref 附加到它。例如:
import React, { createRef, Component } from "react";
import ChildComponent from "./child-component";
class MyComponent extends Component {
componentDidMount() {
const node = this.wrapper.current;
/* Uses DOM node */
}
wrapper = createRef();
render () {
return (
<div ref={this.wrapper}>
<ChildComponent>{this.props.children}</ChildComponent>
</div>
);
}
}
export default MyComponent;`
要解决此问题,只需从访问 dom root id 的 index.js 中删除 React.StrictMode,即可解决问题。
而不是这个:
ReactDOM.render(
<React.StrictMode>
<App />
</React.StrictMode>,
document.getElementById('root')
);
使用这一行:
ReactDOM.render(<App />,document.getElementById('root'));
我不确定它在使用 material-ui 库时是否有帮助,但在很多情况下这会有所帮助:
const nodeRef = React.useRef(null);
return <div>
<CSSTransition ... nodeRef={nodeRef}>
<div ref={nodeRef}> ... </div>
</CSSTransition>
</div>
类似问题: 下面解决了问题:
在ReactDOM.render()
函数中,更改
来自
<React.StrictMode>
<SnackbarProvider>
<App/>
</SnackbarProvider>
</React.StrictMode>
至
<SnackbarProvider>
<React.StrictMode>
<App/>
</React.StrictMode>
</SnackbarProvider>
注意:SnackbarProvider
和 React.StrictMode
标签是相反的。
我以前见过这个错误,当我同时使用 react-bootstrap 和 react-router-dom 时 彼此 。 我替换了
<Link to="/foo">sth</Link>
和
<LinkContainer to="/foo/bar">
<Button>Foo</Button>
</LinkContainer>
并且无需使用 Link 进行导航Link
这是 Material UI 库的问题,在新的 Material UI v5 正式发布之前temporary solution这里
我认为这个问题不是错误,而是弃用警告。库组件仍然有效,但使用了未来版本中将不再可用的功能。因此必须更新库以使用另一个函数来替换旧函数。
在 Semantic UI React 中,这是一个 known issue, most of their components are still using findDOMNode()
. This will be fixed in the Semantic UI React v3,其中所有这些组件都将更新为使用 React.forwardRef()
。
起初我以为我做错了什么,花了很多时间调查,才发现这是一个已知问题。