【问题标题】:Maintaining reactjs element state when removing it from the DOM从 DOM 中删除时保持 reactjs 元素状态
【发布时间】:2015-07-16 15:20:45
【问题描述】:

我正在使用 ReactJS 构建一个网站。我有一个 div,它的内容是根据单选按钮的状态决定的(它改变了媒体的值):

<div className="card_container">
     { this.state.media=="image" ? <MediaCard /> : <TextCard /> }
</div>

在 card_container 中呈现的两个元素都有一个文本字段,我希望它们的内容在状态之间切换时不会被丢弃。例如,如果在 MediaCard 内的文本区域中输入“foo”,切换到 TextCard,然后再切换回 MediaCard,则会丢失在文本区域中输入的文本。

如何维护原始的 MediaCard 元素并仅使用文本及其所有道具和状态重新渲染原始元素?

编辑:目前,我已经通过冒泡包含元素的属性来解决这个问题,然后在我重新渲染这些元素时将它们作为道具传递。不过,这是一个丑陋的解决方案,我宁愿找到一个更好的解决方案......

【问题讨论】:

  • 只是一个想法:也许尝试在 componentWillUnmount() 中克隆对象,以捕获其属性?
  • 我没有尝试过,但即使我尝试添加对该元素的引用(例如 - 如果在 MediaCard 的父级上我添加:this.state.MC = 然后渲染 this.state.MC,它仍然会创建一个全新的元素
  • 我会将状态冒泡给父级。但是,如果这对您来说看起来“丑陋”,为什么不直接使用 CSS 来隐藏/显示处于活动状态的 Card?这样它就不会被破坏。

标签: javascript html reactjs


【解决方案1】:

如果您在渲染时在组件之间切换,那么react 无法判断在重新渲染时是否应该保留文本字段,因此它会与父组件一起重新创建它。解决此问题的方法是使用单个 Card 组件,该组件在 type 参数上运行,而不是两个:

<div className="card_container">
     {<Card type={this.state.media} />}
</div>

这样react 将能够检测到可以保留文本字段。

编辑。如果您的组件层次结构需要两个单独的组件,您可以同时渲染这两个组件,并且一次只有一个可见:

var hasMedia = this.state.media == "image";

<div className="card_container">
    <MediaCard  visible={hasMedia}/>
    <TextCard  visible={!hasMedia}/>
</div>

每个组件都将保持其状态,并且您一次只能在屏幕上显示一个

【讨论】:

  • 我使用 2 张卡,因为它们的外观和行为完全不同。即使我将 media 的值作为属性传递,我仍然需要根据 media 渲染 2 个不同的 react 元素,这种情况会重演......
  • 有道理,我怀疑这就是你有两个组件的原因;不幸的是,这会影响重新渲染组件时 react 所做的优化,因为每次渲染父组件时都会创建一个全新的 MediaCard/TextCard。
  • 您可以尝试将文本作为属性传递给卡片组件,并让卡片在卸载时从父级调用委托方法,但它有点丑陋并增加了组件之间的紧密耦合.
  • @Luoruize:我更新了我的答案并添加了另一个可能的解决方案
  • 感谢@Cristik!我正在考虑做同样的事情。我得到了另一个使用 Flux 的建议,每次渲染时只需将数据模型传递给组件。虽然更优雅,但您的解决方案更适合我,因为我必须在这些组件中显示图像,而且我讨厌它们每次都重新加载。
猜你喜欢
  • 2021-08-02
  • 1970-01-01
  • 2018-06-01
  • 2021-10-30
  • 2014-09-01
  • 2021-06-08
  • 2017-11-22
  • 2013-05-19
  • 1970-01-01
相关资源
最近更新 更多