我有一个外部(组件),可观察对象,我想监听的变化。当对象更新时,它会发出更改事件,然后我希望在检测到任何更改时重新呈现组件。
使用顶级React。渲染这是可能的,但在组件中它不起作用(这是有意义的,因为渲染方法只返回一个对象)。
下面是一个代码示例:
export default class MyComponent extends React.Component {
handleButtonClick() {
this.render();
}
render() {
return (
<div>
{Math.random()}
<button onClick={this.handleButtonClick.bind(this)}>
Click me
</button>
</div>
)
}
}
在内部单击按钮会调用this.render(),但这并不是真正导致呈现发生的原因(您可以在操作中看到这一点,因为由{Math.random()}创建的文本没有改变)。但是,如果我简单地调用this.setState()而不是this.render(),它就可以正常工作。
所以我想我的问题是:React组件需要有状态才能渲染吗?是否有一种方法可以在不改变状态的情况下强制组件按需更新?
使用useEffect作为componentDidMount, componentDidUpdate和componentWillUnmount的组合,如React文档中所述。
要像componentDidMount一样工作,你需要像这样设置你的useEffect:
useEffect(() => console.log('mounted'), []);
第一个参数是一个回调,它将根据第二个参数(一个值数组)触发。如果第二个参数中的任何值发生了变化,您在useEffect中定义的回调函数将被触发。
然而,在我所展示的示例中,我传递了一个空数组作为第二个参数,这将永远不会被更改,因此回调函数将在组件挂载时调用一次。
这是对useEffect的总结。如果不是空值,而是有一个参数,比如:
useEffect(() => {
}, [props.lang]);
这意味着每次道具。Lang改变,你的回调函数将被调用。useEffect实际上不会重新渲染你的组件,除非你在回调函数中管理一些状态,这些状态可能会触发重新渲染。
如果你想要触发一个重新渲染,你的渲染函数需要在你的useEffect中更新一个状态。
例如,在这里,渲染函数开始显示英语作为默认语言,在我的使用效果中,我在3秒后改变了语言,所以渲染被重新渲染并开始显示“西班牙语”。
function App() {
const [lang, setLang] = useState("english");
useEffect(() => {
setTimeout(() => {
setLang("spanish");
}, 3000);
}, []);
return (
<div className="App">
<h1>Lang:</h1>
<p>{lang}</p>
</div>
);
}