2015-08-05 20 views
7

Mi chiedo come funzionano ES6 e cloneElement quando si passa a una funzione. Ho bisogno di fare riferimento allo stato nello stato del componente genitore ma i riferimenti this si riferiscono al componente figlio e non al genitore.Reagire, "questo", cloneElement e es6

Di seguito è riportato il codice in JavaScript normale per farlo funzionare, dopo averlo scritto per la prima volta in ES6 e sbattendo la testa sulla tastiera, ho deciso di vedere se era ES6, quindi ho refactored e funziona perfettamente.

Voglio solo scriverlo in ES6 perché tutto il resto è, ma questo mi ha messo in difficoltà.

Questo è il mio componente ES5:

var Parent = React.createClass({ 
    content: function() { 
    return React.Children.map(this.props.children, function(child) { 
    return React.cloneElement(child, { 
     passThisFunc: this.passThisFunc 
    }) 
    }.bind(this)); 
    }, 

    passthisfunc: function(component) { 
    // returns the components props 
    console.log(this); 

    // Returns the component so I can do component.props.name 
    console.log(component); 
    }, 

    render: function() { 
    return (
     <div> 
     { this.content } 
     </div> 
    ) 
    } 
}); 

E poi nei suoi figli:

var Child = React.createClass({ 
    componentDidMount: function() { 
    this.props.passThisFunc(this); 
    } 

    render: function()..... 
}); 

I componenti non sono poi così diversi in ES6, è davvero quello che fa riferimento quando this viene registrato .

Qualsiasi aiuto nel refactoring (in particolare la componente padre) sarebbe molto apprezzato.

Modifica Ecco l'ES6 Esempio ho provato:

class Parent extends React.Component { 
    content() { 
    return React.Children.map(this.props.children, function(child) { 
    return React.cloneElement(child, { 
     passThisFunc: this.passThisFunc 
    }) 
    }.bind(this)); 
    } 

    passthisfunc(component) { 
    // returns the components props 
    console.log(this); 

    // Returns the component so I can do component.props.name 
    console.log(component); 
    } 

    render() { 
    return (
     <div> 
     { this.content } 
     </div> 
    ) 
    } 
}; 

class Child extends React.Component { 
    componentDidMount() { 
    this.props.passThisFunc(this); 
    } 

    render(){...} 
}; 
+0

Potete per favore correggere gli errori di sintassi nel 'content'? – Bergi

+0

ES6 non cambia nulla su come 'questo' funzioni. Che valore ti aspettavi per "questo" se non "child.props"? – Bergi

+0

Quello che ho in 'content' è essenzialmente lo stesso di quello che ho nella mia attuale implementazione e funziona perfettamente, quali sono gli errori di sintassi? Anche sulla seconda domanda voglio fare qualcosa del tipo: 'this.setState ({test: 'test'})' Quindi immagino che mi aspetto che questo sia uguale al componente padre in modo simile fa in ES5. –

risposta

15

Il autobinding che React.createClass DID was removed per le classi ES6 (vedi anche this article). Quindi dovrete farlo manualmente ora:

… 
    content: function() { 
    return React.Children.map(this.props.children, function(child) { 
    return React.cloneElement(child, { 
     passThisFunc: this.passThisFunc.bind(this) 
    }) 
    }.bind(this)); 
    }, 
… 

Ma non sarebbe davvero fare questo in ES6. Piuttosto, utilizza una funzione di freccia, in primo luogo, che dispone di un lessicale this vincolante:

class Parent extends React.Component { 
    constructor() { 
    super(); 
    this.passthisfunc = (component) => { 
     // returns the parent 
     console.log(this); 

     // Returns the component so I can do component.props.name 
     console.log(component); 
    }; 
    } 
    content() { 
    return React.Children.map(this.props.children, child => 
     React.cloneElement(child, { 
     passThisFunc: this.passThisFunc 
     }); 
    ); 
    } 
    … 
} 
+0

Questa seconda versione è fantastica, grazie mille! –

+0

Nota: le funzioni freccia ricreano la funzione ogni rendering, che è un colpo di micro-perf per essere confrontato con la sintassi molto più pulita. –

+0

@AshleyCoolman Solo quando dichiarato all'interno di 'render' (o un metodo chiamato da esso), che non ho fatto afaik – Bergi

Problemi correlati