【问题标题】:How to pass props to recursive child component and preserve all props如何将道具传递给递归子组件并保留所有道具
【发布时间】:2017-07-02 03:09:53
【问题描述】:

我遇到了一个有趣的问题。我有一个父组件,它有一个对象数组,这些对象被传递给一个 TreeView 的子组件,这意味着它是递归的。我正在向孩子传递一个函数和几个其他道具,以及由孩子递归处理的对象数组。在子项的渲染函数中记录道具时,在第一次渲染时,所有道具都在那里,但是当递归函数在数组中的每个对象中移动时,它会“丢失”所有其他未被递归处理的道具。

组件第一次渲染时props对象为:prop1,prop2,arrayOfObjects

随着递归的发生而重新渲染,子对象中的 props 对象变为:arrayOfObjects。

prop1 和 prop2 消失了。

最终结果是我无法从子级调用父级中的函数,因此我无法根据单击树中的哪个节点来更新状态。我没有使用 redux,因为这是一个样式指南 - 与我们的生产应用程序分开,它仅供开发人员使用,而且很简单,所以如果可能的话,我想从组件中处理所有状态。

还有另一个问题 - 对象数组是我们样式指南中文件的文件夹结构,我需要能够单击列表中的名称,并使用该文件的内容更新视图。当文件没有任何子节点时,这可以正常工作,但是当有子节点时,如果我单击父节点,则会单击子节点。我已经尝试过 e.stopPropagation()、e.preventDefault() 等,但没有任何运气。提前致谢。

家长:

import React, {Component} from 'react'
import StyleGuideStructure from '../../styleguide_structure.json'
import StyleTree from './style_tree'

class StyleGuide extends Component {

constructor(props) {
    super(props)

    let tree = StyleGuideStructure

    this.state = {
        tree: tree
    }

这是我想从孩子那里调用的函数

   setVisibleSection(nodeTitle) {

    this.setState({
      section: nodeTitle
    })

   }

   render() {

     return(

     <TreeNode 
      className="class-name-here" 
      setVisibleSection={this.setVisibleSection.bind(this)} 
      node={this.state.tree}
     />

    )

  }
}

 export default StyleGuide

这基本上就是我在孩子身上所拥有的,在这里作为一个小提琴:

https://jsfiddle.net/ssorallen/XX8mw/

唯一的区别是在切换函数内部,我试图在父级中调用 setVisibleSection,但没有骰子。

这是控制台的照片,显示了组件最初渲染时的道具,然后是递归后:

【问题讨论】:

  • 我添加了上面的图像,显​​示了在递归期间被“清空”的 props 对象。递归后我不再可以访问 setVisibleSection 函数。剩下的唯一道具是节点道具。如果我不将节点道具传递给孩子,所有道具都保持不变。

标签: reactjs recursion tree treeview


【解决方案1】:

我不认为我真的理解你的第二个问题。你能发布一个显示问题的小提琴吗?

我认为您的第一个问题是您需要将道具传递给孩子们。我试图将您的示例转录到您的小提琴中。点击节点可以看到,标题切换到节点的名字。

https://jsfiddle.net/hbjjq3zj/

/**
 * Using React 15.3.0
 *
 * - 2016-08-12: Update to React 15.3.0, class syntax
 * - 2016-02-16: Update to React 0.14.7, ReactDOM, Babel
 * - 2015-04-28: Update to React 0.13.6
 */

class TreeNode extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
    	visible: true,
    };
  }
  
  toggle = () => {
    this.setState({visible: !this.state.visible});
    this.props.setVisibleSection(this.props.node.title)
  };
  
  render() {
  	var childNodes;
    var classObj;

    if (this.props.node.childNodes != null) {
      childNodes = this.props.node.childNodes.map((node, index) => {
        return <li key={index}><TreeNode {...this.props} node={node} /></li>
      });

      classObj = {
        togglable: true,
        "togglable-down": this.state.visible,
        "togglable-up": !this.state.visible
      };
    }

    var style;
    if (!this.state.visible) {
      style = {display: "none"};
    }

    return (
      <div>
        <h5 onClick={this.toggle} className={classNames(classObj)}>
          {this.props.node.title}
        </h5>
        <ul style={style}>
          {childNodes}
        </ul>
      </div>
    );
  }
}

class ParentComponent extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
    	visible: true,
    };
  }
  
  toggle = () => {
    this.setState({visible: !this.state.visible});
  };
  setVisibleSection(nodeTitle) {
    this.setState({
      title: nodeTitle
    })
  }
  render() {
    return (
    	<div>
      	Title: {this.state.title}
      	<TreeNode 
        	node={tree} 
          setVisibleSection={this.setVisibleSection.bind(this)}
        />
      </div>
    );
  }
}




var tree = {
  title: "howdy",
  childNodes: [
    {title: "bobby"},
    {title: "suzie", childNodes: [
      {title: "puppy", childNodes: [
        {title: "dog house"}
      ]},
      {title: "cherry tree"}
    ]}
  ]
};

ReactDOM.render(
  <ParentComponent />,
  document.getElementById("tree")
);
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>

【讨论】:

  • 感谢您查看此内容。在描述中,我将道具传递给孩子们。我正在尝试将该 setVisibleSection 函数作为道具传递给孩子。由于某种原因,它被递归消灭了。它在此处的示例中确实有效,但在我机器上的控制台中,我可以看到对象发生了变化。第一次渲染时的样子,不是递归完成时的样子。我会发一张照片。奇怪。
  • 我看到您将所有道具传递给正在递归的子组件。这解决了这个问题。我将它们传递给孩子,但没有传递给孩子在地图中对自身的引用。谢谢!
猜你喜欢
  • 1970-01-01
  • 2018-07-07
  • 2020-12-19
  • 2018-08-01
  • 1970-01-01
  • 2018-11-25
  • 2020-08-20
  • 1970-01-01
  • 2020-02-29
相关资源
最近更新 更多