Rami Chasygov
Rami Chasygov

Reputation: 2784

Passing arguments from child component React

I try to pass argument from child component to parent. P.S. Snippet below doesn't work if somebody fix this, it would be really great.

class Parent extends React.Component {

  suggestionClick(id) {
    console.log(this.props, id); // {props Object} , undefined
  }

  render(){
    return (
      <ChildComponent click={this.suggestionClick.bind(this)} />
    );
  }
}


const ChildComponent = ({ click }) => (
  <SubChildComponent id="1" click={() => click()} />
);

const SubChildComponent = ({ click, id }) => (
  <div className="subsubcomponent" click={() => click(id)} />
);



ReactDOM.render(
  <Parent />,
  document.getElementById('app')
);
<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="app"></div>

Upvotes: 4

Views: 86

Answers (4)

mindaJalaj
mindaJalaj

Reputation: 448

You can also use es6 arrow function in your parent component, therefore no need to bind this to this function explicitly.

However when we call this function from child along with id to be passed to it, we bind this for passing the id value. Below is the modified code for reference. Hope this helps.

class Parent extends React.Component {

  // make this function as arrow function
  suggestionClick = (id) => {
    console.log(this.props, id); // {props Object} , id
  }

  render(){
    return (
      <ChildComponent click={this.suggestionClick} />
    );
  }
}


const ChildComponent = (props) => (
  <SubChildComponent id="1" click={props.click} />
);

const SubChildComponent = (props) => (
  <div className="subsubcomponent" onClick={props.click.bind(this, props.id)} />
);



ReactDOM.render(
  <Parent />,
  document.getElementById('app')
);

Upvotes: 0

Mayank Shukla
Mayank Shukla

Reputation: 104469

This is because you are not passing the value from ChildComponent to parent component, here:

<SubChildComponent id="1" click={() => click()} />

Use this:

<SubChildComponent id="1" click={(id) => click(id)} />

Or Simply:

<SubChildComponent id="1" click={click} />

Another change is replace click with onClick inside SubChildComponent.

Working Code:

class Parent extends React.Component {

  suggestionClick(id) {
    console.log(this.props, id); // {props Object} , undefined
  }

  render(){
    return (
      <ChildComponent click={this.suggestionClick.bind(this)} />
    );
  }
}


const ChildComponent = ({ click }) => (
  <SubChildComponent id="1" click={(id) => click(id)} />
);

const SubChildComponent = ({ click, id }) => (
  <div className="subsubcomponent" onClick={() => click(id)}>Click</div>
);



ReactDOM.render(
  <Parent />,
  document.body
);
<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>

Upvotes: 3

stevejay
stevejay

Reputation: 894

In ChildComponent, just pass the click property directly to the SubChildComponent:

const ChildComponent = ({ click }) => (
  <SubChildComponent id="1" click={click} />
);

Upvotes: 1

Jo&#227;o Cunha
Jo&#227;o Cunha

Reputation: 10307

  1. Don't use divs to trigger clicks. The right way is using a button for example
  2. The right function handler is onClick not just click

class Parent extends React.Component {

  suggestionClick(id) {
    alert(id);
    console.log(this.props, id); // {props Object} , undefined
  }

  render(){
    return (
      <ChildComponent click={this.suggestionClick.bind(this)} />
    );
  }
}


const ChildComponent = ({ click }) => (
  <SubChildComponent id="1" click={click} />
);

const SubChildComponent = ({ click, id }) => (
  <button className="subsubcomponent" onClick={() => click(id)}>click me</button>
);



ReactDOM.render(
  <Parent />,
  document.getElementById('app')
);
<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="app"></div>

Upvotes: 6

Related Questions