2016-07-27 6 views
21

Hier ist eine grundlegende Komponente. Sowohl die <ul> als auch die <li> haben onClick-Funktionen. Ich möchte nur den OnClick auf den <li> auslösen, nicht den <ul>. Wie kann ich das erreichen?Reagieren verhindern, dass Event-Bubbling in verschachtelten Komponenten bei Klick

Ich habe mit e.preventDefault(), e.stopPropagation(), vergeblich gespielt.

class List extends React.Component { 
    constructor(props) { 
    super(props); 
    } 

    handleClick() { 
    // do something 
    } 

    render() { 

    return (
     <ul 
     onClick={(e) => { 
      console.log('parent'); 
      this.handleClick(); 
     }} 
     > 
     <li 
      onClick={(e) => { 
      console.log('child'); 
      // prevent default? prevent propagation? 
      this.handleClick(); 
      }} 
     > 
     </li>  
     </ul> 
    ) 
    } 
} 

// => parent 
// => child 
+0

I gleiche Frage hatte, https://stackoverflow.com/questions/44711549/how-to-prevent-react-component-click-event-bubble-to-document –

Antwort

28

Ich hatte das gleiche Problem. Ich fand stopPropagation tat arbeiten. Ich würde das Listenelement in eine separate Komponente aufgeteilt, wie es so:

class List extends React.Component { 
    handleClick = e => { 
    // do something 
    } 

    render() { 
    return (
     <ul onClick={this.handleClick}> 
     <ListItem onClick={this.handleClick}>Item</li> 
     </ul> 
    ) 
    } 
} 

class ListItem extends React.Component { 
    handleClick = e => { 
    e.stopPropagation(); 
    this.props.onClick(); 
    } 

    render() { 
    return (
     <li onClick={this.handleClick}> 
     {this.props.children} 
     </li>  
    ) 
    } 
} 
+0

awesome! Es hat funktioniert wie ein Zauber! – asifsid88

+0

Sollte 'this.props.handleClick() 'in der' ListItem' Komponente 'this.props.click' sein? – ZeroDarkThirty

+0

Ja! Du hast vollkommen recht. Ich werde meine Antwort aktualisieren –

16

Reagieren verwendet Ereignis Delegation mit einem einzigen Ereignis-Listener auf dem Dokument für Ereignisse, die Blase, wie ‚Klick‘ in diesem Beispiel, was bedeutet, stoppt Ausbreitung nicht möglich; Das reale Ereignis hat sich bereits in der Zeit, in der Sie mit ihm interagieren, in React ausgebreitet. stopPropagation auf Reacts synthetischem Ereignis ist möglich, weil React die Weitergabe synthetischer Ereignisse intern handhabt.

stopPropagation: function(e){ 
    e.stopPropagation(); 
    e.nativeEvent.stopImmediatePropagation(); 
}