将道具传递给嵌套的子组件

时间:2019-11-28 08:52:24

标签: javascript reactjs redux

这是我的结构:

Main.js (Parent)
MainContainer.js
|
|_ Article.js
       |
       |__ Comments.js

现在,我想在评论组件(递归组件)上设置点击处理程序,并调度操作。

这是我关于comment.js的代码

class Comment extends Component {
    deleteComment = (id) => {
        this.props.handleDelete(id)
    }
    render() {
        var comment = this.props.comment
        return (
            <div className={styles.commentsWrapper}>
                <ul>
                    <li>
                        <div className={styles.commentsName}>
                            <a onClick={() => this.deleteComment(comment.id)} className={styles.commentsNameRight}>
                            </a>
                        </div>
                        <p>{comment.body}</p>
                        {comment.children.length > 0 && comment.children.map(function(child) {
                            return <Comment comment={child} key={child.id}/>
                        })}

                    </li>
                </ul>
            </div>
        );
    }
}
export default Comment;

和Article.js:

 class Article extends Component {    

        handleDeleteComment = (id) => {
            this.props.deleteComment(id)
        }


        render() {
            return (
                <article className={styles.articleItem}>
                        {this.props.comments.map(item =>
                            <Comment handleDelete={this.handleDeleteComment} comment={item} key={item.id}/>)}
                </article>
            );
        }
    }


    export default Article;

还有Main.js

class Main extends Component {
    deleteComment = (id) => {
        this.props.deleteCommentRequest(id)
    }

    render() {
        return (
            <div className="">
                <Header />
                <section className="container">
                    <div>
                        {
                            !this.props.articles.loading && this.props.articles.articles? (
                                <div>
                                    {this.props.articles.articles.map(item =>
                                        <Article
                                        bodytext={item.selftext}
                                        key={item.id}
                                        comments={item.finalComments}
                                        deleteComment={this.deleteComment}
                                        />)}
                                </div>

                            ) : (
                                <div className={styles.loading}> <Spin /> </div>
                            )
                        }
                    </div>
                </section>
            </div>
        );
    }
}

export default Main;

所以我在这里所做的是:将deleteComment作为道具从主体传递到文章,再将handleDelete从文章传递到评论。

不确定这是否是一个好方法吗?

预先感谢

2 个答案:

答案 0 :(得分:2)

这种模式对于2到3个组件的深度没有问题,因为这是数据应该如何从子级流到祖先的方式。但是,如果您的应用程序变得越来越重,请考虑使用其他状态管理,例如redux,其中维护全局状态,任何组件都可以订阅它并调度操作。 here的更多内容。

或者,您也可以使用带有useContext的React Hooks实现相同的功能,在其中您可以设置上下文,任何子组件都可以订阅它。示例:

const MyContext = React.createContext();

export default function App({ children }) {
  const [items, setItems] = React.useState([]);
  return (
    <MyContext.Provider value={{ items, setItems }}>
      {children}
    </MyContext.Provider>
  );
}

export { MyContext };

现在,只要位于App组件的子级中的任何子级中,您都可以执行以下操作:

import {MyContext} from './filename';

function TodoItem() {
  const { items, setItems } = React.useContext(MyContext);
  return (
    <div onClick={() => setItems(1)}>

    </div>
  );
 }

答案 1 :(得分:1)

您可以使用上下文API将道具放在包装中,并可以从子组件轻松访问。

youtube上有来自wesbos的精彩教程

class App extends Component {
  render() {
    return (
      <MyProvider>
        <div>
          <p>I am the app</p>
          <Family />
        </div>
      </MyProvider>
    );
  }
}


class MyProvider extends Component {
  state = {
    name: 'Wes',
    age: 100,
    cool: true
  }
  render() {
    return (
      <MyContext.Provider value={{
        state: this.state,
        growAYearOlder: () => this.setState({
          age: this.state.age + 1
        })
      }}>
        {this.props.children}
      </MyContext.Provider>
    )
  }
}