0

I have a React app which has this code:

<div className={ mainCss } data-appmode={ AppMode.MAIN } onClick={ this.handleAppModeClick.bind(this) }>
     <div className="NavLinkIconContainer"></div>
     <div>Main</div>
</div>

When I click on div with className="NavLinkIconContainer" the handleAppModeClick function does not work correctly. The function fires but does not pick up the data-* attribute. However, when I click on the div with Main as it's content it works perfectly picking up the data-* attribute. Why is this and how do I fix it?

Brian Tompsett - 汤莱恩
  • 5,753
  • 72
  • 57
  • 129
Scott Kingdon
  • 351
  • 1
  • 2
  • 9
  • 1
    Possible duplicate of [How to access custom attributes from event object in React?](https://stackoverflow.com/questions/20377837/how-to-access-custom-attributes-from-event-object-in-react) – Emile Bergeron Nov 06 '19 at 20:19

2 Answers2

2

You can the data-appmode value from event.currentTarget.dataset.

  • event - the event object
  • currentTarget - the element with the onClick
  • dataset - an easy access to data-* values

class Demo extends React.Component {
  handleAppModeClick = event => console.log(event.currentTarget.dataset.appmode);

  render() {
    return (
      <div
        data-appmode="example" 
        onClick={this.handleAppModeClick}>
           <div className="NavLinkIconContainer">NavLinkIconContainer</div>
           <div>Main</div>
      </div>
    )
  }
}

ReactDOM.render(
  <Demo />,
  root
)
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>

<div id="root"></div>
Ori Drori
  • 183,571
  • 29
  • 224
  • 209
1

Ori Drori's suggestion will work. Alternatively, you can write your component as

<div className={ mainCss } data-appmode={ AppMode.MAIN } onClick={ ()=>this.handleAppModeClick(AppMode.MAIN) }>
 <div className="NavLinkIconContainer"></div>
 <div>Main</div>

This will fire off the function with a hard-coded argument. In my opinion, it's a little bit cleaner than using event.currentTarget.dataset. That being said, I am sure that others disagree with me, and if the solution works, it works.

Alternatively, you can use

 handleAppModeClick = event => console.log(event.target.getAttribute('data-appmode'));

to get the data from the actual element.

NegativeFriction
  • 527
  • 2
  • 14