React onClick function in map function React onClick function in map function reactjs reactjs

React onClick function in map function


Use an arrow function as the function given to map instead and this will be what you expect:

if (this.props.data) {  var recipes = this.props.data.map((recipe, i) => {    return <div key={i} className="col-8 offset-col-1 f-l relative m-t-10">      <div className="col-6 f-l">        <p className="col-8 f-l">{recipe.title}</p>        <button className="f-l" onClick={this.handleClick}>Voir la recette</button>      </div>    </div>;  });}

Why this is the case is explained in detail here. Arrow functions don't provide their own this binding, but instead retains the this value of the enclosing lexical context.


This is how I would tackle a similar situation.

import React from "react";import ReactDOM from "react-dom";const stuff = ["one", "two", "three"];class App extends React.Component {  constructor(props) {    super(props);    this.state = {      isToggleOn: true    };    this.handleClick = this.handleClick.bind(this);  }  handleClick(val) {    console.log(val);  }  getStuff() {    var elements = stuff.map((value, key) => {      return (        <li key={key} onClick={() => this.handleClick(value)}>          {value}        </li>      );    });    return elements;  }  render() {    return <ul>{this.getStuff()}</ul>;  }}const rootElement = document.getElementById("root");ReactDOM.render(<App />, rootElement);

here is the sandbox -> https://codesandbox.io/embed/1rqw081oj7


You have to use this in map arguments or arrow function.

 this.props.data.map(function(recipe, i) {            return  <div key={i} className="col-8 offset-col-1 f-l relative m-t-10">                        <div className="col-6 f-l">                            <p className="col-8 f-l">{recipe.title}</p>                            <button className="f-l" onClick={this.handleClick}>Voir la recette</button>                        </div>                    </div>;        }, this)

Why?

Read here.

If a thisArg parameter is provided to map, it will be used as callback's this value. Otherwise, the value undefined will be used as its this value.

For a better undestanding of this scope check here. Explains what are in this in different context like Simple function call, as an object method, as arrow function, etc. Also explain how control the scope thanks to bind, call and apply.