如何将道具传递给递归子组件并保留所有道具

Posted

技术标签:

【中文标题】如何将道具传递给递归子组件并保留所有道具【英文标题】: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 函数。剩下的唯一道具是节点道具。如果我不将节点道具传递给孩子,所有道具都保持不变。 【参考方案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 函数作为道具传递给孩子。由于某种原因,它被递归消灭了。它在此处的示例中确实有效,但在我机器上的控制台中,我可以看到对象发生了变化。第一次渲染时的样子,不是递归完成时的样子。我会发一张照片。奇怪。 我看到您将所有道具传递给正在递归的子组件。这解决了这个问题。我将它们传递给孩子,但没有传递给孩子在地图中对自身的引用。谢谢!

以上是关于如何将道具传递给递归子组件并保留所有道具的主要内容,如果未能解决你的问题,请参考以下文章

如何将道具传递给vue中的子组件

如何将值从组件传递给道具并设置状态

如何将道具传递给vue中的兄弟组件和子组件

将道具传递给***组件中的状态

反应不将道具传递给组件

如何在 React 中将不同的道具从父组件传递给多个子组件?