nl *_*pkr 3 reactjs redux react-redux
根组件
<Provider store={Store}>
<AppLayoutContainer>
{this.props.template}
</AppLayoutContainer>
</Provider>
Run Code Online (Sandbox Code Playgroud)
应用布局容器
....some code
return(
<div className={`AppLayoutContainer`}>
<Modal isOpen={isModalShown} .... />
<div>{children}</div>
</div>
)
....some code
function mapStateToProps(state) {
const { app } = state;
return {
isModalShown: app.isModalShown
}
}
export default connect(mapStateToProps)(AppLayoutContainer);
Run Code Online (Sandbox Code Playgroud)
每次isModalShown从 Redux获取 Applayoutcontainer 时,我的整个应用程序都在重新渲染,而且非常糟糕。我所需要的只是重新渲染 Modal 组件,不要触摸我的children. 我认为使用ShouldComponentUpdate方法是可能的,但我真的不明白该怎么做。
有任何想法吗 ?我知道有人在他的项目中做到了这一点,并且可以为此提供一些最佳实践建议。谢谢
阅读所有答案,是的,将 Modal 与 Store 连接是一个很好的解决方案,但是如果
1)我希望模态组件像或组件一样纯(可重用)?
2)我需要isModalShown在 AppLayoutContainer 中使用?
return(
<div className={`AppLayoutContainer`}>
<Modal isOpen={isModalShown} .... />
<div>{children}</div>
</div>
)
Run Code Online (Sandbox Code Playgroud)
谢谢你的回答,但我能用这个做什么
主要问题是我在显示Modal组件时需要模糊所有内容,因为我知道blur()只能应用于要工作的内容(而不是覆盖我的内容的绝对位置 div),并且这样做
return(
<div className={`AppLayoutContainer`}>
<Modal isOpen={isModalShown} .... />
<div className={isModalShown ? 'blured' : null }>{children}</div>
</div>
)
Run Code Online (Sandbox Code Playgroud)
但是我的整个应用程序每次出现时都会重新渲染Modal,我需要冻结它。在这里构建容器child并执行的解决方案shouldcomponentupdate不好,React 如何比较整个组件?它只比较 props 中的非不可变字段。
任何解决方案?
你应该做的是没有通过isModal的AppLayoutContainer的mapStateToProps功能,而是connect在Modal自身。
mapStateToProps该更改的任何结果都将导致connected 组件重新渲染。在您的情况下,您的mapStateToProps connectedAppLayoutContainer返回isModalShown导致您AppLayoutContainer重新渲染的值。
如果您只想重新渲染Modal本身,那么只需
export default connect(state => ({isOpen: state.app.isModalShown}))(Modal)
Run Code Online (Sandbox Code Playgroud)
在您的Modal文件中,或者如果您更喜欢在单独的文件中。
还要isModalShown从 中删除道具,AppLayoutContainer因为您不需要它,并且因为将它留在那里意味着AppLayoutContainer每次isModalShown更改时仍会重新渲染(这是您要修复的)。
更新有关问题的更新:
问题 1:
你可以拥有纯 Modal
export default function Modal(props) {
return <span>Open={props.isOpen}</span>;
}
Run Code Online (Sandbox Code Playgroud)
然后,您可以为特定用途制作特定的 Modal:
import Modal from './modal';
import { connect } from 'react-redux';
export default const AppLayoutModal = connect(state => ({isOpen: state.app.isModalShown}))(Modal);
Run Code Online (Sandbox Code Playgroud)
对于各种单独的模态,您可以多次执行此操作。事实上,这就是为什么使用纯组件是个好主意的原因。
问题 2:
如果你想使用isModalShowninAppLayoutContainer那么你有一些选择:
isModalShownvia connect,因此大组件AppLayoutContainer不会改变。子组件可以并且确实独立于其父组件进行更新。更新 2
要模糊整个应用程序,只需向应用程序添加一个类。子组件不会重新渲染。Redux 会阻止孩子渲染,因为它注意到孩子没有使用isModalShown. 生成的 React 元素与之前的渲染完全相同(引用)。React 看到它是同一个元素并且知道不更新整个树。这是有效的,因为 React 元素是不可变的。您的整个应用程序将不会重新渲染。实际上,React只会从 class 属性中添加或删除类。
如果您的孩子不使用 Redux 来防止渲染沿着树走,那么您可以将孩子包装在 Redux 连接的组件中。或者,您可以使用shouldComponentUpdate来阻止渲染子项。
Bare React 要求您从根向树下发送数据。Redux 要求您在需要的地方将数据注入到树中。后者的好处是不需要重新渲染其他任何东西。如果没有 Redux,除非组件用于停止传播,否则每次更改时都会重新渲染整个树shouldComponentUpdate。但是,这不仅会停止当前组件的渲染,还会停止所有子组件的渲染。Redux 消除了这一点,因为子组件可以在没有父组件合作或不知情的情况下更新它们的 props。
简而言之:到处使用 Redux 以提高速度。
| 归档时间: |
|
| 查看次数: |
5417 次 |
| 最近记录: |