Sha*_*oux 1 reactjs react-native react-hooks
我遇到了图像闪烁的问题,因为尽管使用了 React.memo,而且它的 props 或状态都没有改变,但它还是无缘无故地渲染了。
我在这里成功地正确使用了 React.memo 来完成这项工作,BUUUT,出于我不明白的原因,如果我在父组件中使用高阶组件,备忘录将不再工作,我得到我的眨眼问题又来了。
这是代码:
import * as React from 'react';
import { Text, View, StyleSheet } from 'react-native';
let interval = null
const Icon = ({ name }) => {
// We emulate a rerender of the Icon by logging 'rerender' in the console
console.log('rerender')
return <Text>{name}</Text>
}
const Memo = React.memo(Icon, () => true)
const withHOC = (Comp) => (props) => {
return <Comp {...props}/>
}
export default function App() {
const [state, setState] = React.useState(0)
const name = 'constant'
// Change the state every second
React.useEffect(() => {
interval = setInterval(() => setState(s => s+1), 1000)
return () => clearInterval(interval)
}, [])
// Remove this line and replace NewView by View to see the expected behaviour
const NewView = withHOC(View)
return (
<NewView>
<Memo name={name} />
</NewView>
);
}
Run Code Online (Sandbox Code Playgroud)
我不明白为什么我的 HOC 会破坏记忆,而且我不知道如何防止我的应用程序闪烁并仍然能够使用 HOC...
您正在渲染函数中重新创建 HOC。因此,React 无法使该组件的任何子组件在渲染之间保持一致。
如果将 HOC 创建移到渲染之外,那么它就会起作用!
const Text = 'span';
const View = 'div';
let interval = null
const Icon = ({ name }) => {
// We emulate a rerender of the Icon by logging 'rerender' in the console
console.log('rerender')
return <Text>{name}</Text>
}
const Memo = React.memo(Icon, () => true)
const withHOC = (Comp) => (props) => {
return <Comp {...props}/>
}
// move it out here!
//
const NewView = withHOC(View)
//
function App() {
const [state, setState] = React.useState(0)
const name = 'constant'
// Change the state every second
React.useEffect(() => {
interval = setInterval(() => setState(s => s+1), 1000)
return () => clearInterval(interval)
}, [])
// Remove this line and replace NewView by View to see the expected behaviour
return (
<NewView>
<Memo name={name} />
</NewView>
);
}
ReactDOM.render(<App />, document.querySelector('#root'));Run Code Online (Sandbox Code Playgroud)
<script crossorigin src="https://unpkg.com/react@16/umd/react.development.js"></script>
<script crossorigin src="https://unpkg.com/react-dom@16/umd/react-dom.development.js"></script>
<div id="root"></div>Run Code Online (Sandbox Code Playgroud)
编辑:我在另一个答案中看到了您的评论。
好的,但是我如何在我的组件中使用 HOC?因为我需要向临时提供道具和状态......
如果你确实需要在组件内创建 HOC,你可以用 包装它useMemo,这也可以工作,因为如果依赖项useMemo不改变,React 将在渲染之间保留你的 HOC 引用(注意:如果你的钩子这将不起作用每次渲染的依赖关系都会发生变化)。
function App() {
// ...
const NewView = useMemo(() => withHOC(View), []);
}
Run Code Online (Sandbox Code Playgroud)
虽然这可行,但可能有点不稳定。一般来说,钩子和 HOC 不是一起使用的模式。React 核心团队创建了 hooks 来取代 HOC。在你继续沿着这条路走之前,我会尝试看看你是否可以将你的 HOC 写成一个钩子。我想你会发现它更加自然。
| 归档时间: |
|
| 查看次数: |
1473 次 |
| 最近记录: |