简体   繁体   中英

this.props returns undefined with array.map((item, i)

I am trying to pass the content of a given array item as a prop, and later use it to trigger certain REST functions, but when I pass item.room and console.log(this.props.myProp) later, I find that what prints is undefined. I have followed every resource I could find step by step, yet it seems that props is haunting my console. Please help!

Failing Code;

class Lights extends Component {
  lumin()  {
    console.log(this.props.lumer + " clicked!")
  }
  render() {
    return(
      <div className="Lights">
        <div className="link-wrapper">
          {[
            {
              room: 'Office'
            },
            {
              room: 'Office Bathroom'
            },
            {
              room: 'Neekon Bedroom'
            },
            {
              room: 'Ryan Room'
            },
            {
              room: 'Homework Room'
            },
            {
              room: 'Living Room'
            },
            {
              room: 'Gallery'
            },
            {
              room: 'Guest Bathroom'
            },
            {
              room: 'Dining Room'
            },
            {
              room: 'Kitchen'
            },
            {
              room: 'Master Bedroom'
            },
            {
              room: 'Family Room'
            }
          ].map((item, i) => {
            return (
              <a onClick={this.lumin.bind(this)} lumer={item.room} className="toggle-text">
              {item.room}</a>)
          })}
        </div>
      </div>
    )
  }
}

Your problem is you are trying to look at the props of a child component from the parent component. Your lumin() function is on your Lights component, but your passing lumer as a prop to your <a> component.

The easiest fix would be instead of

onClick={ this.lumin.bind(this) }

instead do:

onClick={ () => this.lumin(item.room) }

and pass in the room to the function directly (not try to read this.props.lumer ).

However, the more appropriate solution would be to replace your <a> with a custom component and then move the lumin() function to it.

// Lights component
[].map(item => <RoomLight lumer={ item.room } key={ i } />)

// RoomLight component
class RoomLight extends React.Component {
    lumin() { console.log(this.props.lumer + ' clicked'); }

    render() {
      return <a onClick={ this.lumin.bind(this) }>{ this.props.lumer }</a>;
    }
}

And ideally, don't use arrow functions when rendering. It creates a performance hit. Instead, bind() it in the constructor:

class RoomLight extends React.Component {
    lumin() { console.log(this.props.lumer + ' clicked'); }

    constructor(props) {
      super(props);

      this.lumin = this.lumin.bind(this);
    }

    render() {
      return <a onClick={ this.lumin }>{ this.props.lumer }</a>;
    }
}

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