【问题标题】:React: Data rendering on second click, but not on firstReact:第二次点击时数据呈现,但不是第一次
【发布时间】:2020-09-22 08:23:59
【问题描述】:

我有一个模式显示我在道具中收到的数据。当我打开模式时,我应该会看到从我的道具中显示的选择数据。但是,模式在我第一次打开时为空,第二次填充。

如果我继续更改道具中的数据,模式在第一次新点击时保持不变,并在第二次新点击时刷新。

我试过用setTimeout 强制它,弄乱componentDidMountcomponentDidUpdate 和其他生命周期方法的组合,但似乎没有任何效果。我确定这与我在componentDidMount 中使用prevData 参数有关。但即使反应开发工具显示this.state.pricesData 更新,当我尝试从状态渲染时,我每次都会得到空白。当我调用控制台日志作为 setState 的回调时,我在控制台日志中得到一个空数组括号(我可以展开它以显示所有正确的数组数据,但我猜这是在日志之后异步填充的)。

代码如下:

import React, { Component } from "react";

import "../../App.css";

let explanations = [];

export default class ExplanationModal extends Component {
  constructor(props) {
    super(props);
    this.state = {
      pricesData: [],
    };
  }

  static getDerivedStateFromProps(nextProps, prevState) {
    if (nextProps.pricesData !== prevState.pricesData) {
      return { pricesData: nextProps.pricesData };
    } else {
      return null;
    }
  }

  // to allow for async rendering
  getSnapshotBeforeUpdate(prevProps) {
    if (prevProps.pricesData !== this.state.pricesData) {
      return this.state.pricesData;
    }
  }

  componentDidMount = () => {
    this.setState({ pricesData: this.props.pricesData }, () =>
      console.log(this.state.pricesData)
    );
  };

  componentDidUpdate = (prevData) => {
    this.renderExp(prevData.pricesData);
  };

  renderExp = (data) => {
    explanations = [];
    data.forEach((set) =>
      explanations.push({ title: set.titel, explanation: set.explenation })
    );
  };

  onClose = () => {
    this.props.hideModal();
  };

  render() {
    return (
      <div className="modal">
        <div>
          {explanations.map((item) => (
            <span>
              <h4>{item.title}</h4>
              <p>{item.explanation}</p>
            </span>
          ))}
        </div>
        <button onClick={this.onClose} className="update">
          Close
        </button>
      </div>
    );
  }
}

【问题讨论】:

    标签: javascript reactjs state react-props react-lifecycle


    【解决方案1】:

    你必须保持你的解释数组在你的状态。然后在新数据到达时更新状态。因为如果你不更新状态,react 不会触发重新渲染。

    你的构造函数应该是

        super(props);
        this.state = {
          pricesData: [],
          explanations : []
        };
      }
    

    你的 renderExp 函数应该是

    renderExp = (data) => {
        explanations = [];
        data.forEach((set) =>
          explanations.push({ title: set.titel, explanation: set.explenation })
        );
        this.setState({ explanations })
      };
    

    在你的渲染函数中

    render() {
        return (
          <div className="modal">
            <div>
              {this.state.explanations.map((item) => (
                <span>
                  <h4>{item.title}</h4>
                  <p>{item.explanation}</p>
                </span>
              ))}
            </div>
            <button onClick={this.onClose} className="update">
              Close
            </button>
          </div>
        );
      }
    }
    

    这样您将在数据到达时获得更新的数据。

    【讨论】:

    • 感谢您的反馈!我认为面临的问题是超过最大更新深度。看到我在componentDidMount 中调用renderExp,在renderExp 中我正在设置状态,它陷入了更新/重新渲染循环。这就是为什么我在课外保存解释。任何想法如何解决这个问题?
    • 跟进:在componentDidMount 中调用renderExp 使用this.state.pricesData 代替,并进行了治疗。谢谢!
    猜你喜欢
    • 2016-10-24
    • 2021-01-03
    • 2021-08-08
    • 1970-01-01
    • 2014-06-04
    • 1970-01-01
    • 2017-07-03
    • 2016-07-14
    • 2022-11-22
    相关资源
    最近更新 更多