简体   繁体   中英

How can I pass data to a component without props in React?

in the question I mean this. Imagine that I want to show a component Called "Form" and inside of "Form" there is a list of components called "checkboxex"

The normal way to do that is something like this:

const checkboxes = [1, 2, 3];
<Form checkBoxes={checkboxex} />

and then inside Form I just map that (Array.map)

I want to know is there is a way to do this:

const checkboxes = [1, 2, 3];

<Form>
   checkboxes.map(id =>
    <Checkbox key={id} id={id}/>
</Form>

Can anyone explain me if it is possible and what's the difference ? Thanks a lot !

Anything passed inside a component like that is automatically converted to the children prop. You can access them inside Form like this:

//...
render() {
  <div>
    {this.props.children}
  </div>
}
//...

The pattern that you have mentioned is children prop pattern, where the nested JSX gets passed to the component as the children.

When you include JS as part of JSX , you will have to wrap them in {}

<Form>
  { checkboxes.map(id => <Checkbox key={id} id={id} />) }
</Form>

Your Form component render method would look something like this.

render() {
  <div>
    {this.props.children}
  </div>
}

If the children that you passed is a function, you would just invoke it in the Form component.

<Form>
  {() => {
    return checkboxes.map(id => <Checkbox key={id} id={id} />)
  }}
</Form>

You just invoke the children cause it is passed as a function.

render() {
      <div>
        {this.props.children()}
      </div>
    }

In a general manner, both of the two methods are the same. They render some JSX in the parent component ( Form ), somehow.

In the first one, you are passing the data to the parent, then somehow you want to use this data in its children.

In the second one, you intend to map the data, then pass a child component to the parent with this data. So, actually, you are passing the parent a prop: children . Your question does not reflect your needs here. But, you are asking the difference. The difference may be the logic of how you will use and what will you do in this Form and with its children.

Think about this scenario. You have a handleClick method in the Form component and you want to pass this to your child components, each Checkbox . Here is the two versions.

Without children prop

 const checkboxes = [1, 2, 3]; class App extends React.Component { render() { return ( <div> <Form checkboxes={checkboxes} /> </div> ); } } const Form = props => { const handleClick = id => console.log("id is", id); return ( <div> {props.checkboxes.map(id => ( <Checkbox id={id} key={id} handleClick={handleClick} /> ))} </div> ); }; const Checkbox = props => { const handleClick = () => props.handleClick(props.id); return ( <div onClick={handleClick} style={{ padding: "10px" }}> This is Checkbox and id is <strong>{props.id}</strong> .Click me and look the console. </div> ); }; ReactDOM.render(<App />, document.getElementById("root")); 
 <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> <div id="root"></div> 

With children prop

 const checkboxes = [1, 2, 3]; class App extends React.Component { render() { return ( <div> <Form> {checkboxes.map(id => ( <Checkbox id={id} key={id} /> ))} </Form> </div> ); } } const Form = props => { const handleClick = id => console.log("id is", id); return ( <div> {React.Children.map(props.children, child => React.cloneElement(child, { handleClick }) )} </div> ); }; const Checkbox = props => { const handleClick = () => props.handleClick(props.id); return ( <div style={{ padding: "10px" }} onClick={handleClick}> This is Checkbox and id is <strong>{props.id}</strong> .Click me and look the console. </div> ); }; ReactDOM.render(<App />, document.getElementById("root")); 
 <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> <div id="root"></div> 

You can see the struggle here :) So, it is up to you choosing one of them according to your needs. If you don't set up a logic as in the second example you can use the children prop. Actually, you can create reusable components with this logic. I just tried to show an edge case here.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM